我使用下面的程序通过指针访问二维数组。
#include<stdio.h>
void main()
{
int num[3][2]={ {00,01},{10,11},{20,21} };
int i,j;
printf("-----------------------------------");
/* Treating 2d array as 1d array of each row */
for(i=0;i<3;i++)
{
printf("\nThe Address(&num[%d]) is %u \n \n<= WHICH IS THE SAME AS =>\n \n(num[%d]) %u \t",i,&num[i],i,num[i]);
printf("[*(num+%d)] %u \t [(num+%d)] %u ",i,*(num+i),i,(num+i));
printf("\n The Value is %d \n",*num[i]);
printf("\n -----------------------------------");
}
}
这是输出:
-----------------------------------
The Address(&num[0]) is 2140353424
<= WHICH IS THE SAME AS =>
(num[0]) 2140353424 [*(num+0)] 2140353424 [(num+0)] 2140353424
The Value is 0
-----------------------------------
The Address(&num[1]) is 2140353432
<= WHICH IS THE SAME AS =>
(num[1]) 2140353432 [*(num+1)] 2140353432 [(num+1)] 2140353432
The Value is 10
-----------------------------------
The Address(&num[2]) is 2140353440
<= WHICH IS THE SAME AS =>
(num[2]) 2140353440 [*(num+2)] 2140353440 [(num+2)] 2140353440
The Value is 20
-----------------------------------
我了解程序中发生的事情,并且我知道 *(num+i)
用于访问每一行的地址。
但是,为什么*(num+i)
和(num+i)
都指向同一个地址?
要访问特定行(第 i 行)的值,我们使用 **(num+i)
这是有道理的,因为 *(num+i)
指向第一个一维数组的行地址,我们可以使用另一个间接运算符来取消引用该指针。
但是 *(num+i)
和 (num+i)
怎么会指向同一个地址呢?
这个编译器依赖吗?或者一些未定义的行为?
请提供尽可能多的信息。
最佳答案
多维数组连续存储在内存中。这是您的数组的内存布局:
[0][0] [0][1] [1][0] [1][1] [2][0] [2][1]
+------+------+------+------+------+------+
| 00 | 01 | 10 | 11 | 20 | 21 |
+------+------+------+------+------+------+
|_____________|_____________|_____________|
^ ^ ^
num[0] num[1] num[2]
在我的机器上,int 的大小为 4 个字节。
num
的类型为 int (*)[2]
- 它是指向 2 个整数的数组的指针。语句 num+1
是一个指针算法,结果是将 8 个字节(即两个整数的大小)添加到 num
数组开始的地址。
取消引用后 - *(num+1)
它仍然是一个指针,它指向与 num+1
相同的地址。您可以检查这段短代码以了解发生了什么:
#include <stdio.h>
int main(void)
{
int num[3][2]={ {00,01},{10,11},{20,21} };
int (*fp)[2] = num+1;
int* fpp = *(num+1);
printf("%d\n", (void*)fpp == (void*)fp);
return 0;
}
输出为 1 - 这些指针拥有相同的内存地址。
关于c - 使用指针时将二维数组用作多个一维数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25849486/