千万不要忘了,当你把一个手指指向别人的时候,你还有另外3个手指指向了你自己... ---多疑间谍的格言
多维数组的内存分布
多维数组在系统编程中并不常用。所以,毫不奇怪的是,C语言并未像其他语言所要求的那样定义了详细的运行时程序来支持这个特性。对于某些结构(如动态数组),程序员必须使用指针显式分配和操纵内存,而不是由编译器自动完成。另外还有一些结构(作为参数的多维数组),在C语言中并没有一般的形式来表达。
char pea[4][6];
有些人把二维数组看作是排列在一张表格中的一行行的一维数组,事实上系统绝不允许程序按照这种方式来存储数据。单个数据的存储和引用实际上是以线性排列在内存中的。
数组下标的规则告诉我们如何计算左值pea[i][j];首先找到pea[i]的位置,然后根据偏移量[j]取得字符。因此,pea[i][j]将被编译器解析为:
*(*(pea + i) + j)
但是(这正是关键所在),pea[i]的意思将随pea的定义的不同而变化。首先让我们看一下C语言中最常见、最重要的数据结构:指向字符串的一维指针数组。
/*
** memory distribution of multi-dimension array.
*/
#include <stdio.h>
#include <stdlib.h>
int main( void ){
char pea[][3] = {"abc", "def", "hij", "klm"};
int i, j;
int first_d_size = (int)(sizeof(pea) / sizeof(*pea));
int doubly_d_size = (int)(sizeof(*pea) / sizeof(**pea));
for( i = 0; i < first_d_size; ++i ){
for( j = 0; j < doubly_d_size; ++j ){
printf( "&pea[%d][%d] = %p, pea[%d][%d] = %c, *(*(pea + %d) + %d) = %c\n",
i, j, &pea[i][j], i, j, pea[i][j], i, j, *(*(pea + i) + j) );
}
printf( "\n" );
}
return EXIT_SUCCESS;
}
输出: