Arduino - Iterate through C array efficiently

2019-05-09 22:58发布

问题:

I have the following array:

PROGMEM prog_uint16_t show_hide_info[] = { 4216, 8900, 4380, 580, 500, 600, 500, 580, 1620, 580, 500, 600, 500, 580, 500, 600, 480, 600, 500, 580, 1620, 580, 1620, 600, 500, 580, 1620, 580, 1620, 600, 1600, 600, 1620, 580, 1620, 600, 500, 580, 1620, 580, 500, 600, 1600, 600, 500, 580, 1620, 580, 500, 600, 1620, 580, 1620, 600, 480, 600, 1620, 580, 500, 600, 1600, 600, 500, 580, 1620, 580, 500, 600, 39300, 8860, 2160, 580, 0 };

I'd like to be able to loop through this array and execute the following methods accordingly:

pulseIR(4216);
delayMicroseconds(8900);
pulseIR(4380);
delayMicroseconds(580);
...

This is what I have so far, which is obviously way off track:

unsigned int* get(prog_uint16_t code[]) {
  unsigned int c;

  while ((c = pgm_read_word(code++))) {
    //pulseIR(c); ??
    //delayMicroseconds(c+1); ??
  }
}

Not quite sure what I'm meant to be doing with c to be honest.

Due to lack of sleep, I can't for the life of me make sense of the following documentation on PROGMEM:

http://arduino.cc/en/Reference/PROGMEM

回答1:

First you'll need some short hand to find the end of the array. If its a fixed number of values, then the compiler can calculate it this way to find the count of int16 values:

PROGMEM prog_uint16_t show_hide_info[] = { 4216, 8900, 4380, 580, ....etc
int arraySize = sizeof(show_hide_info) / sizeof(prog_uint16_t);

Then if you want to have a function that goes thru your array just once, the function can be declared this way:

void cycleThruArrayOnce(prog_uint16_t *pInArray, int nLimit) {
 for (int i=0;i<nLimit;i=i+2) {
   pulseIR(pgm_read_word(pInArray++));
   delayMicroseconds(pgm_read_word(pInArray+));
 }
}

And it can be called from your main program this way:

cycleThruArrayOnce(show_hide_info, arraySize);


回答2:

I ended up using the following code. Does what I need it to do. Not sure if it's the most efficient way however. I'm open to any suggestions and am willing to accept answers over my final one.

void sendCode(prog_uint16_t inArray[], int nLimit) {

  unsigned int arr[nLimit];
  unsigned int c;
  int index = 0;

  while ((c = pgm_read_word(inArray++))) {
    arr[index] = c;
    index++;
  }

  for (int i = 0; i < nLimit; i=i+2) {
    delayMicroseconds(arr[i]);
    pulseIR(arr[i+1]);
  }

}


回答3:

Would this bit be a little faster

    for (int i = 0; i < nLimit; i=i+2) {
    delayMicroseconds(arr[i]);
    pulseIR(arr[i+1]);
  }

if

for (int i = 0; i < nLimit; i++) {
    delayMicroseconds(arr[i]);
    i++;
    pulseIR(arr[i]);
  }