考虑以下二维数组:
array= {
{'a','b','c'},
{'d','e','f'},
{'g','h','i'}
}
语句:array
,将指向数组第一个字节的地址,语句:&array[0][0]
将指向数组第一个元素的第一个字节。
这两者有什么区别?他们不是一回事吗?我们如何使用简单的代码证明这两者之间的差异?
答案 0 :(得分:2)
有三件事代表相同的地址:array
(衰减到&array[0]
),array[0]
(衰变到&array[0][0]
)和&array
虽然这三件事导致相同的地址,但他们代表不同的东西,因此具有不同的类型。
表达式array
和&array[0]
的类型为char(*)[3]
。
表达式array[0]
和&array[0][0]
的类型为char*
。
最后,表达式&array
的类型为char(*)[3][3]
。
可能更容易理解它是否显示更多"图形化":
内存中的数组看起来像这样
+-----+-----+-----+-----+-----+-----+-----+-----+-----+ | 'a' | 'b' | 'c' | 'd' | 'e' | 'f' | 'g' | 'h' | 'i' | +-----+-----+-----+-----+-----+-----+-----+-----+-----+
如果我们放入所有指针真正指向的地方,我们有
+-----+-----+-----+-----+-----+-----+-----+-----+-----+ | 'a' | 'b' | 'c' | 'd' | 'e' | 'f' | 'g' | 'h' | 'i' | +-----+-----+-----+-----+-----+-----+-----+-----+-----+ ^ ^ ^ ^ ^ | | | | | | | &array[1] &array[2] &array[3] | | | | | | | &array[1][0] &array[2][0] &array[3][0] | | | | &array[0][1] | | | &array (&array)[1] | &array[0] | &array[0][0]
当然,array[3]
超出范围,但是可以在使用指针标记结尾迭代数组时使用它(即在指针小于例如{{1}时迭代) })
答案 1 :(得分:0)
首先,你的声明中有错误,你把点(。)代替逗号(,)。
在C中数组是连续存储的,“数组”是这里的助记符,所以数组和& array [0] [0]的值是相同的。
答案 2 :(得分:0)
char array[3][3] = {
{'a','b','c'},
{'d','e','f'},
{'g','h','i'}
};
char *a = &array[0][0]; // compiles
char (*b)[3] = array; // compiles
char *c = array; // error
char (*d)[3] = &array[0][0]; // error
答案 3 :(得分:0)
#include <stdio.h>
int main(int argc, char* argv[]){
int arr[3][3] = {{'a','b','c'},
{'d','e','f'},
{'g','h','i'}
};
//value of the first elemnt
printf("%c\n",arr[0][0]);
//3 ways to print the address of the first element
printf("%p\n",arr);
printf("%p\n",(arr+0));
printf("%p\n",&arr[0][0]);
//the value of the first element in the second row
printf("%c\n",arr[1][0]);
//2 ways to use the address of the first element in the second row
printf("%p\n",&arr[1][0]);
printf("%p\n",(arr+1));
return 0;
}
我希望这段代码能够更清晰,看看评论。