使用三重指针将内存分配给3D数组

我必须使用三指针将内存分配给3D数组。

#include  int main() { int m=10,n=20,p=30; char ***z; z = (char***) malloc(sizeof(char**)*m*n*p); return 0; } 

这是正确的做法吗?(我认为我所做的是不正确的。)

要完全分配3D动态数组,您需要执行以下操作:

 #include  #include  int main() { int m=10,n=20,p=30; char ***z; z = malloc(m * sizeof(char **)); assert(z != NULL); for (i = 0; i < m; ++i) { z[i] = malloc(n * sizeof(char *)); assert(z[i] != NULL); for (j = 0; j < n; ++j) { z[i][j] = malloc(p); assert(z[i][j] != NULL); } } return 0; } 

释放数据留给读者练习。

没有必要在C中malloc()的返回值。

如果你希望直接存储m * n * p字符(并自己计算地址),那么你当然不应该按照char **的大小来扩展分配。

你的意思是:

 int m = 10, n = 20, p = 30; char *z = malloc(m * n * p * sizeof *z); 

这将分配10 * 20 * 30 = 6000字节。 这可以被视为形成高度为p的立方体,沿着垂直轴的每个“切片”是n * m个字节。

由于这是用于手动寻址,您不能使用例如z[k][j][i]来索引,而是必须使用z[k * n * m + j * m + i]

如果你不需要在一个连续的块中分配内存(通常情况下是IME),你可以这样做:

 char ***z; z = malloc(sizeof *z * m); // allocate m elements of char ** if (z) { int i; for (i = 0; i < m; i++) { z[i] = malloc(sizeof *z[i] * n); // for each z[i], if (z[i]) // allocate n elements char * { int j; for (j = 0; j < n;j++) { z[i][j] = malloc(sizeof *z[i][j] * p); // for each z[i][j], if (z[i][j]) // allocate p elements of char { // initialize each of z[i][j][k] } } } } } 

请注意,您需要以相反的顺序释放此内存:

 for (i = 0; i < m; i++) { for (j = 0; j < n; j++) free(z[i][j]; free(z[i]); } free(z); 

如果你真的需要在一个连续的块中分配内存,你有几个选择。 您可以分配单个块并手动计算偏移量:

 char *z = malloc(sizeof *z * m * n * p); // note type of z! ... z[i * m + j * n + k] = some_value(); 

当你完成后,你只需要做一次free

 free(z); 

如果您有支持可变长度数组的C99编译器或C11编译器,您可以执行以下操作:

 int m=..., n=..., p=...; char (*z)[n][p] = malloc(sizeof *z * m); 

这将z声明为指向n x p char数组的指针,并且我们分配m这样的元素。 内存是连续分配的您可以使用普通的3-d数组索引语法( z[i][j][k] )。 与上述方法一样,您只需要一个free通话:

 free(z); 

如果您没有支持VLA的C99编译器或C11编译器,则需要生成np编译时常量,例如

 #define n 20 #define p 30 

否则最后一个方法将无效。

编辑

在这种情况下, m不需要是编译时常量,只需要np

你需要以下嵌套循环 –

 z = (char**)malloc(sizeof(char*) * m); for (int i = 0; i < m; ++i) { *(z + i) = (char*)malloc(sizeof(char*) * n); for (int j = 0; j < n; ++j) { *(*(z + i)) = (char)malloc(p); } } 

可能不是完全准确的,但它应该是这些方面的东西。

你想要sizeof(char)而不是sizeof(char**)因为后者会给你一个指针的大小,在大多数现代系统中它将是4个字节而不是你期望的1个。