Here is what you want:
int (*p)[5][6] = new int[3][5][6];
Since C++11 you can ask the compiler to decuce the type of p
for you:
auto p = new int[3][5][6];
You don't need anything special to delete such array:
delete [] p;
Logic behind the choice of the type is simple:
In this line: int *p = new int[10]
you're creating an array of 10 ints
and you use pointer to int
to store the address.
In general case, if you're allocating an array of N Ts
(where N
is the size and T
is the type), you use pointer to T
to store the address.
Same rule can be applied to multidimensional arrays, because they are in fact nested 1D arrays.
When you try to allocate multidimensional array: p = new int[4][5][6]
, you're creating an array of 4 arrays of 5 arrays of 6 ints
. Thus you need a pointer to array of 5 arrays of 6 ints
, which is int (*p)[5][6]
.
In other words, int [3][4][5]
can be viewed as 1D array of size 3
. It consists of other arrays of type int [4][5]
. Each of these arrays has size 4
and consists of other arrays of type int [5]
, which in turn contain 5
int
s.
P.S. Authors of other answers seem to favor using int ***
and allocating memory for each nested array separately. Doing so may seem smart, but in fact it's much slower and dangerous (if you mess up your memory management). The only advantage of that trick is that it provides the convenient interface we all used to (p[z][y][x]
).
But there is a much better solution: int *p = new int[x_sz * y_sz * z_sz];
. You would need to convert 3D indices to 1D index (p[x + x_sz * (y + z * y_sz)]
instead of p[z][y][x]
) for it to work, but in my opinion it's still more convenient (and definitely faster).
Of course, in real code, you should use std::vector
to store such array and write your own wrapper class, which would compute the index automatically.