我对C中指针和数组的问题感到困惑.
让我们先看一段代码:
//case 1
int **a;
a = (int **)malloc(sizeof(int*)*m);
for(i = 0; i < m; i++)
    a[i] = (int *)malloc(sizeof(int)*n);
//case 2
int b[m][n];
然后,我们知道,b内存中的布局如下:
b[0][0] b[0][1] ... ... b[m-1][n-1]
并且,内存中的布局如下:
a
 \
 _\|
 a[0]  a[1] ... a[m-1]
  |    |
  |    |
  |   \|/
  |   a[1][0] a[1][a] ... a[1][n-1]
 \|/
a[0][1] a[0][2] ... a[0][n-1]
所以,我的问题是:由于a[0..m-1][0..n-1]存储在内存中不连续地,为什么我们可以使用下标操作[]上a?换句话说,为什么a[i][j]可以得到正确的元素,就像b[i][j]这样做?
编译器单独处理表达式的每个部分。a[i][j]和之间的主要区别b[i][j]在于,由于a是指向 的指针int,因此 的地址计算会a[i]计算指针的数量,但是,由于b是 的数组的数组int,因此 的地址计算会b[i]计算数组的数量。C 使用表达式每个部分的类型来确定如何计算它。
口译的步骤a[i][j]是:
a是一个指向 的指针的指针int。a[i]被定义为*(a + i).a+i是i超出 wherea点的元素。由于a指向 的指针int,我们对i的指针进行计数int以确定新地址。int,因此*对其应用会产生一个指向 an 的指针int。a[i][j]被定义为*(a[i] + j). 我们已经评估了该a[i]部分。a[i] + j是j超出 wherea[i]点的元素。由于a[i]指向int对象,我们对j int对象进行计数以确定新地址。int,应用*它会产生一个int。口译的步骤b[i][j]是:
b是 的m数组的数组n int。b是一个数组,因此它被转换为指向其第一个元素的指针,即 的数组n int。b[i]被定义为*(b + i).b + i是i超出 whereb点的元素。由于b已转换为指向 数组的指针n int,我们对i数组进行计数n int以确定新地址。n int,因此*对其应用会产生一个 数组n int。int.b[i][j]被定义为*(b[i] + j). 我们已经评估了该b[i]部分。b[i] + j是j超出 whereb[i]点的元素。由于它指向int,我们通过计数j int来确定新地址。int,应用*它会产生一个int。| 归档时间: | 
 | 
| 查看次数: | 355 次 | 
| 最近记录: |