在C语言中声明一个数组但不指定大小

6

当像这样声明一个数组时:

int array[][] = {
    {1,2,3},
    {4,5,6}};

我收到了一个错误提示:"数组类型具有不完整的元素类型"。
发生了什么?
3个回答

25

对于一个 N 维数组(N>0),你需要定义前 N-1 个维度的大小,只有一个维度可以留给编译器来确定,而且这个维度必须是第一个维度。

你可以这样写:

int d1[] = { ... };
int d2[][2] = { ... };
int d3[][2][3] = { ... };
等等。

1
很抱歉成为第13个点赞的不幸者,但我发现这非常有帮助 :) - Doug Molineux

5

需要指定除最高维度以外的所有维度。原因是编译器将分配一个大块内存,而不是一个指向它们自己小数组的指针数组。换句话说,

int array[][3][4] = ...;

本段代码将分配一个大小为3x4x(你在这里声明了多少个3x4数组)的连续内存区域。因此,当你在代码的其他部分编写以下内容时:

array[1][2][3] = 69;

为了找到在内存中写入69的位置,它从地址(数组)开始,然后向前跳转12*sizeof(int)以到达array[1],再加上2*4*sizeof(int)以到达array[1][2],最后加上3*sizeof(int)以到达array[1][2][3]的开头。与此相比,例如写入:
int ***array = new int**[n];
for(i=0; i<n; i++)
{
  array[i] = new int * [3];
  for(j=0; j<4; j++)
    array[i][j] = new int[4];
}

(如果我的语法不是很准确,抱歉...已经有一段时间没写C语言代码了)。在这个例子中,数组指向一个长度为n*sizeof(int**)字节的代码块。这个数组的每个元素指向另一个大小为3*sizeof(int*)字节长的数组。这些数组的每个元素又指向另一个大小为4*sizeof(int)字节长的数组。在这种情况下,需要在内存中跟随几个不同的指针才能找到写入69的位置,而不是计算出array[1][2][3]位于地址(array + something)。


1

你必须至少告诉它除了最大的尺寸之外的所有尺寸。

例如,在你的情况下

int array[][3] = {
    {1,2,3},
    {4,5,6}};

不完全正确,你需要指定除最外层之外的所有内容,对吧? - falstro
你需要正确地选择 n-1 个最小维度。 - Martin Beckett

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接