int main()
{
matrix[2][4] = {{11,22,33,99},{44,55,66,110}};
int **ptr = (int**)matrix;
printf("%d%d",**matrix,*ptr);
}
但是当一个二维数组作为参数传递时,它被转换为(*矩阵)[2]。 编译器将这个数组存储为什么类型...是存储为2-d数组还是双指针或指向数组的指针。如果它作为数组存储,它在不同的情况下如何解释不同的情况。请帮我理解。
答案 0 :(得分:38)
2d数组是否为双指针?
没有。你的程序的这一行不正确:
int **ptr = (int**)matrix;
This answer deals with the same topic
如果你想要具体的图像如何实现多维数组:
多维数组的规则与普通数组的规则没有什么不同,只是将“内部”数组类型替换为元素类型。数组项直接相继存储在内存中:
matrix: 11 22 33 99 44 55 66 110
----------- the first element of matrix
------------ the second element of matrix
因此,要解决元素matrix[x][y]
,请使用the base address of matrix + x*4 + y
(4是内部数组大小)。
当数组传递给函数时,它们会衰减到指向第一个元素的指针。如你所知,这将是int (*)[4]
。然后,类型中的4
将告诉编译器内部类型的大小,这就是它工作的原因。在对类似指针执行指针运算时,编译器会添加元素大小的倍数,因此对于matrix_ptr[x][y]
,您得到matrix_ptr + x*4 + y
,这与上面的完全相同。
演员ptr=(int**)matrix
因此不正确。一次,*ptr
表示存储在矩阵地址的指针值,但没有。其次,在程序的内存中没有指向matrix[1]
的指针。
注意:本文中的计算假定为sizeof(int)==1
,以避免不必要的复杂性。
答案 1 :(得分:10)
没有。多维数组是单个内存块。块的大小是尺寸乘以元素类型的大小的乘积,并且每对括号中的索引通过剩余尺寸的尺寸的乘积偏移到阵列中。所以..
int arr[5][3][2];
是一个包含30 int
s的数组。 arr[0][0][0]
给出第一个,arr[1][0][0]
给出第七个(偏移量为3 * 2)。 arr[0][1][0]
给出第三个(偏移量为2)。
数组衰减的指针将取决于级别; arr
衰减到指向3x2 int数组的指针,arr[0]
衰减到指向2元素int数组的指针,而arr [0] [0]衰减到指向int的指针。
但是,您也可以拥有一个指针数组,并将其视为多维数组 - 但它需要一些额外的设置,因为您必须将每个指针设置为其数组。此外,您丢失了有关数组中数组大小的信息(sizeof
将给出指针的大小)。另一方面,您可以使用不同大小的子数组并更改指针指向的位置,这在需要调整大小或重新排列时非常有用。像这样的指针数组可以像多维数组一样被索引,即使它的分配和排列方式不同,sizeof
也不会总是以相同的方式表现。这种设置的静态分配示例是:
int *arr[3];
int aa[2] = { 10, 11 },
ab[2] = { 12, 13 },
ac[2] = { 14, 15 };
arr[0] = aa;
arr[1] = ab;
arr[2] = ac;
完成上述操作后,arr[1][0]
为12
。但是,不是将int
1 * 2 * sizeof(int)
字节超过数组arr
的起始地址,而是在int
字节处找到的0 * sizeof(int)
超过地址由arr[1]
指出。此外,sizeof(arr[0])
相当于sizeof(int *)
而非sizeof(int) * 2
。
答案 2 :(得分:2)
在C中,理解多维数组并不需要特别了解。它们的工作方式与从未特别提及的方式完全相同。您需要知道的是,您可以创建任何类型的数组,包括数组。
所以当你看到:
int matrix [2] [4];
试想一下,“matrix
是一个由2个东西组成的数组 - 这些东西是4个整数的数组”。适用于数组的所有常规规则。例如,matrix
可以很容易地衰减成指向其第一个成员的指针,就像任何其他数组一样,在本例中是一个包含四个整数的数组。 (当然,这可能会腐烂。)
答案 3 :(得分:0)
如果您可以将堆栈用于该数据(小体积),那么您通常会定义矩阵:
int matrix[X][Y]
如果要在堆中分配(大容量),通常会定义:
int** matrix = NULL;
然后使用malloc / calloc分配两个维度。 您可以将2d数组视为int **,但这不是一个好习惯,因为它会降低代码的可读性。除此之外
**matrix == matrix[0][0] is true