Search

6.5 — Multidimensional Arrays

The elements of an array can be of any data type, including arrays! An array of arrays is called a multidimensional array.

Since we have 2 subscripts, this is a two-dimensional array.

In a two-dimensional array, it is convenient to think of the first (left) subscript as being the row, and the second (right) subscript as being the column. This is called row-major order. Conceptually, the above two-dimensional array is laid out as follows:

[0][0]  [0][1]  [0][2]  [0][3]  [0][4] // row 0
[1][0]  [1][1]  [1][2]  [1][3]  [1][4] // row 1
[2][0]  [2][1]  [2][2]  [2][3]  [2][4] // row 2

To access the elements of a two-dimensional array, simply use two subscripts:

Initializing two-dimensional arrays

To initialize a two-dimensional array, it is easiest to use nested braces, with each set of numbers representing a row:

Although some compilers will let you omit the inner braces, we highly recommend you include them anyway, both for readability purposes and because of the way that C++ will replace missing initializers with 0.

Two-dimensional arrays with initializer lists can omit (only) the leftmost length specification:

The compiler can do the math to figure out what the array length is. However, the following is not allowed:

Just like normal arrays, multidimensional arrays can still be initialized to 0 as follows:

Note that this only works if you explicitly declare the length of the array! Otherwise, you will get a two-dimensional array with 1 row.

Accessing elements in a two-dimensional array

Accessing all of the elements of a two-dimensional array requires two loops: one for the row, and one for the column. Since two-dimensional arrays are typically accessed row by row, the row index is typically used as the outer loop.

In C++11, for-each loops can also be used with multidimensional arrays. We’ll cover for-each loops in detail later.

Multidimensional arrays larger than two dimensions

Multidimensional arrays may be larger than two dimensions. Here is a declaration of a three-dimensional array:

Three-dimensional arrays are hard to initialize in any kind of intuitive way using initializer lists, so it’s typically better to initialize the array to 0 and explicitly assign values using nested loops.

Accessing the element of a three-dimensional array is analogous to the two-dimensional case:

A two-dimensional array example

Let’s take a look at a practical example of a two-dimensional array:

This program calculates and prints a multiplication table for all values between 1 and 9 (inclusive). Note that when printing the table, the for loops start from 1 instead of 0. This is to omit printing the 0 column and 0 row, which would just be a bunch of 0s! Here is the output:

1    2    3    4    5    6    7    8    9
2    4    6    8    10   12   14   16   18
3    6    9    12   15   18   21   24   27
4    8    12   16   20   24   28   32   36
5    10   15   20   25   30   35   40   45
6    12   18   24   30   36   42   48   54
7    14   21   28   35   42   49   56   63
8    16   24   32   40   48   56   64   72
9    18   27   36   45   54   63   72   81

Two dimensional arrays are commonly used in tile-based games, where each array element represents one tile. They’re also used in 3d computer graphics (as matrices) in order to rotate, scale, and reflect shapes.

6.6 -- C-style strings
Index
6.4 -- Sorting an array using selection sort

89 comments to 6.5 — Multidimensional Arrays

  • Haider

    Hi,
    Do multidimensional arrays allocate more memory than standard arrays?

    • Hi Haider!

      The standard doesn't force a specific implementation, so there is no general answer to your question.

      Both arrays can store 10 ints.

      Assuming x86_64 architecture with sizeof(int)=4 and sizeof(void*)=8; no compiler optimization; and ignoring the compiler-generated information block:

      One way of implementing multidimensional arrays is:
      @a takes up 8 bytes for the pointer to the first element and 4 bytes for each element. 8B + (10 * 4B) = 48B

      @b takes up 8 bytes for the pointer to the first element, each sub-array takes up 8 bytes for the pointer to their first elements, and each int takes up 4 bytes. 8B + (5 * 8B) + (5 * 2 * 4B) = 88B

      Conclusion: The more sub-arrays there are, the more memory is used.

      GCC's way of implementing multidimensional arrays is:
      A multidimensional array is a one-dimensional array. All elements are stored one after the other in memory, resulting the the same memory usage as one-dimensional arrays.

  • hrmn

    This means, initialize the first elements to 1 and 2, and the rest of the elements "as if they had static storage duration". There is a rule in C saying that all objects of static storage duration, that are not explicitly initialized by the programmer, must be set to zero.

    i read this here https://stackoverflow.com/questions/15520880/initializing-entire-2d-array-with-one-value

    can you please explain this , will it mean the array indices whose default value is set 0 as if static will have file scope? and what else automatically falls into static storage duration ? and does every data type is default 0 in this storage?
    and why you didn't used {} instead of {0}?
    sorry for so many questions..
    Thanks

    • Alex

      Nope, because that's a C rule. C++ rules for initialization of arrays are here: https://en.cppreference.com/w/cpp/language/aggregate_initialization

      In particular: "If the number of initializer clauses is less than the number of members and bases (since C++17) or initializer list is completely empty, the remaining members and bases (since C++17) are initialized by their default initializers, if provided in the class definition, and otherwise (since C++14) by empty lists, in accordance with the usual list-initialization rules (which performs value-initialization for non-class types and non-aggregate classes with default constructors, and aggregate initialization for aggregates)."

      If you look up value initialization (https://en.cppreference.com/w/cpp/language/value_initialization), you'll see this: "...otherwise, the object is zero-initialized.", which is what happens here for the elements that don't have initializers specified.

  • KKR

    Can someone explain the output for the below program??

    Output:
    21
    18
    21

  • KKR

    • nascardriver

      Hi KKR!

      @Alex Do you have an explanation for why Line 8 in @KKR's code is a thing? I can't find any information about it. Probably because I don't know what to search for.

  • Will

    Hello, why when I make a multidimensional array like this
    std::array<std::array<int, 3>, 3> arr{ { { 1, 2, 3 },{ 4, 5, 6 },{ 7, 8, 9 } } }
    I cant access it as in your example std::cout << array[0][1][2]
    The last one says "Expression must have pointer to object"

    • nascardriver

      Hi Will!

      Two issues,
      1] Your array is two-dimensional (3x3), but you're trying to access it like a three-dimensional array. The deepest you can go on a two-dimensional array is arr[x][y], not arr[x][y][z].
      2] You named your variable 'arr' but you're trying the access 'array'. That's what's causing your error.

  • Micah

    Maybe it's just for education purposes, but otherwise wouldn't you keep it simple and create a "int multiply(int x, int y){}" function and just make it so "array[row][col] = multiply(row, col)"  in a for loop?

  • CuRSeD

    how can I set the value of 2d array from the user?

    int a, b;

    cout << "Enter first value :  " ;
    cin >> a ;
    cout << "Enter second value : " ;
    cin >> b ;
    // i will get error

    int myArray[a][b]

  • can we use vectors as multi-dimensional arrays?
    if yes, how?

    • Alex

      You could have a vector of vectors. But you're maybe better off allocating a single dimensional vector and use math to map two coordinates down to one.

Leave a Comment

Put all code inside code tags: [code]your code here[/code]