choose an array from a multidimensional array

hello!

total noob here so i may be approaching this the wrong way totally.
i’m trying to make my program read values sequentially from an array, so far so good:

int myarray[10] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};

(...)

void loop() {

int i;
for (i = 0; i < 9; i = i + 1) { 

usbMIDI.sendNoteOn(myarray[i], 127, 1);

as that last line says, what i’m trying to do is send items from the array/s as midi notes.

in order to introduce more variation, i wanted several arrays to choose from.
i thought having a bunch of them inside a main array would work:

int myarray[2][2] = { {3, 4}, {6, 7} };

but when i try to access those nested arrays, i get errors, of course.

any pointers on how to do this, or perhaps a completely different approach to get to the same result?

MANY THANKS!

How about posting the code that is giving you the problem? You were good at posting the code that does NOT give you a problem.

hi
well, i did not even get THAT far, cause i dont really know how to deal with the nested arrays.

so the moment i add the multidimensional array, then:

usbMIDI.sendNoteOn(myarray[i], 127, 1);

does not work

A Google search for "arduino multidimensional arrays" came up with a couple tutorials:
https://www.tutorialspoint.com/arduino/arduino_multi_dimensional_arrays.htm

i dont really know how to deal with the nested arrays.

Start with something simple

byte theArray[][3] = {{11, 12, 13}, {14, 15, 16}, {17, 18, 19}, {20, 21, 22}, {23, 24, 25}};

void setup()
{
  Serial.begin(115200);
  for (int row = 0; row < 5; row++)
  {
    for (int col = 0; col < 3; col++)
    {
      Serial.print(theArray[row][col]);
      Serial.print(" ");
    }
    Serial.println();
  }
}

void loop()
{
}

i tried to apply this to my goal, ie send those values as midi notes using usbMIDI.sendNoteOn. sorry if this is terribly obvious, but how do i tell the program to choose those arrays and play them?

i tried this, but did not work as i expected:

{
 for (int row = 0; row < 3; row++)
 {
   for (int col = 0; col < 3; col++)
   {

     usbMIDI.sendNoteOn(theArray[row][col], 127, 1);
     delay(333);
     usbMIDI.sendNoteOff(theArray[row][col], 0, 1);
   }
 }
}

THANKS!

Post ALL the code. The snippet is useless.

Also define "did not work as I expected".

sorry. by did not work as i expected i meant that it did not do what i was asking in my first post on this thread, that is, a program that would read values from different arrays and send them as midi notes. here is the code.

 #include <MIDI.h>
 
 MIDI_CREATE_INSTANCE(HardwareSerial, Serial1, MIDI);
 
 const int channel = 1; 
 int myarray[2][8] = { {29, 33, 36, 41, 29, 35, 38, 41}, {38, 38, 38, 36, 38, 38, 38, 36} };

 void setup() {
   MIDI.begin();
 
 }
 
 void loop() {

{
 for (int row = 0; row < 2; row++)
 {
   for (int col = 0; col < 8; col++)
   {

     usbMIDI.sendNoteOn(myarray[row][col], 127, 1);
     delay(333);
     usbMIDI.sendNoteOff(myarray[row][col], 0, 1);
   }
 }
}

 }

now, since my noobiness is making me struggle with this multidimensional array, is there a less advanced, less elegant, but easier to understand for a beginner way to do this? like having multiple arrays, rather than one with nested arrays. sorry if that’s a dumb question but would that be a possibility? and how would i access those?

thanks

just to clarify, i know i can declare multiple arrays, what i mean is how do i read them from the bit that reads from the array in my code, namely:

for (i = 0; i < 7; i = i + 1) {
usbMIDI.sendNoteOn(myarray[i], 127, 1);
delay(333);
usbMIDI.sendNoteOff(myarray[i], 0, 1);
}

how would i dynamically change that “myarray” to something else so that it would read another array?
cheers

If you have defined a data array as follows:

int myarray[2][8] = { {29, 33, 36, 41, 29, 35, 38, 41}, {38, 38, 38, 36, 38, 38, 38, 36} };

You can call a function with the address ("&") of either the first or second set of elements, as follows:

void setup() {
  Serial.begin(9600);
  int myarray[2][8] = { {29, 33, 36, 41, 29, 35, 38, 41}, {38, 38, 38, 36, 38, 38, 38, 36} };
  print_values(&myarray[0][0], 8);
  print_values(&myarray[1][0], 8);
}

void loop() {}

void print_values(int *array, int n) {
  for (int i = 0; i < n; i++) {
    Serial.print(array[i]);
    Serial.print(", ");
  }
  Serial.println();
}

Result:

29, 33, 36, 41, 29, 35, 38, 41,
38, 38, 38, 36, 38, 38, 38, 36,

rrrrrrr:
is there a less advanced, less elegant, but easier to understand for a beginner way to do this? like having multiple arrays, rather than one with nested arrays. sorry if that’s a dumb question but would that be a possibility? and how would i access those?

Maybe this will help, maybe not. With multiple arrays it’d look like this:

byte note0[8];
byte note1[8];
byte note2[8];
byte noten[8];
// ad nauseum

To send note0 you need a statement like send note0. Then you’d need another statement for note1. And so on for each note. The number of send statements will add up quickly. With a multi-dimensional array you can select which note you want by manipulating the first array index.

I took the liberty of modifying and reformatting @jremington’s demo snippet to, it is to be hoped, make the code more closely portray the concept in a visual way.

void setup() {
  Serial.begin(9600);
  int myarray[2][8] = {
    {29, 33, 36, 41, 29, 35, 38, 41},
    {38, 38, 38, 36, 38, 38, 38, 36}
  };

  for (int row = 0; row < 2; row++ ) {
    for (int column = 0; column < 8; column++) {
      Serial.print(myarray[row][column]);
      Serial.print(", ");
    }
    Serial.println();
  }
} // end setup

void loop() {}

Simply, the outer row loop sets which group of eight values is referenced while the inner column loop steps through the values in that set.

A short tutorial on multi-dimensional arrays.

rrrrrrr:
sorry. by did not work as i expected i meant that it did not do what i was asking in my first post on this thread, that is, a program that would read values from different arrays and send them as midi notes. here is the code.

 #include <MIDI.h>

MIDI_CREATE_INSTANCE(HardwareSerial, Serial1, MIDI);

const int channel = 1;
int myarray[2][8] = { {29, 33, 36, 41, 29, 35, 38, 41}, {38, 38, 38, 36, 38, 38, 38, 36} };

void setup() {
  MIDI.begin();

}

void loop() {

{
for (int row = 0; row < 2; row++)
{
  for (int col = 0; col < 8; col++)
  {

usbMIDI.sendNoteOn(myarray[row][col], 127, 1);
    delay(333);
    usbMIDI.sendNoteOff(myarray[row][col], 0, 1);
  }
}
}

}

That code appears to send the value held in each column of each row successively to the MIDI device. It does that by referring to each row (itself an array) and each column of the selected array. Is that not what you want ?

Try printing the value that it is sending as it does it. Do you see what you expect ?

rrrrrrr:
just to clarify, i know i can declare multiple arrays, what i mean is how do i read them from the bit that reads from the array in my code …

how would i dynamically change that “myarray” to something else so that it would read another array?
cheers

The code @jremington posted in Reply #9 does the “dynamic” selection that you’re requesting. The array’s “row” index (number in the first ‘’ pair after the name) is “selecting” a sub-array which can then be indexed using the “column” entry (number in the second ‘’ pair after the name).

To perhaps make that clearer, you could also write that code as:

void setup() {
  Serial.begin(115200);
  delay(2000);
  int myarray[2][8] = { {29, 33, 36, 41, 29, 35, 38, 41}, {38, 38, 38, 36, 38, 38, 38, 36} };
  print_values(myarray[0], 8);
  print_values(myarray[1], 8);
}

void loop() {}

void print_values(int *array, int n) {
  for (int i = 0; i < n; i++) {
    Serial.print(array[i]);
    Serial.print(", ");
  }
  Serial.println();
}

Here, each call to ‘print_values’ successively selects the “rows” and passes them to the function as individual one-dimension arrays. When you pass the name of a one-dimension array to a function, you’re really passing a pointer to the first element in that array (i.e. its memory address). Because the function has no way of knowing how many elements are in the array, you must also pass its size (8 in this case).

rrrrrrr:

 #include <MIDI.h>

MIDI_CREATE_INSTANCE(HardwareSerial, Serial1, MIDI);

// …
  MIDI.begin();

Why are you using two MIDI libraries at the same time?
Remove everything to do with the MIDI library, and keep the usbMidi stuff.

Pieter

  int myarray[2][8] = { {29, 33, 36, 41, 29, 35, 38, 41}, {38, 38, 38, 36, 38, 38, 38, 36} };
  print_values(myarray[0], 8);
  print_values(myarray[1], 8);

Constructions like that work, but make the code harder to understand.

jremington:
Constructions like that work, but make the code harder to understand.

Seems like a rather subjective statement, but OK. And, I did say "perhaps".