一 多维数组元素的的地址
为了更形象、更直观的描述,我们先定义一个二维数组,然后以这个二维数组来描述其地址
int arr[3][4]=
{
{1,2,3,4},
{5,6,7,8},
{9,10,11,12}
};
-
在学习一维数组与指针后,我们知道:数组名就是地址
-
而延伸到二维数组,地址是这样的:
-
我们先把整个二维数组抽象为一个父数组,里边的一维数组就是它的元素,
-
把二维数组里边的一维数组抽象成子数组.
-
以上边定义的二维数组为例:
-
"arr"就是整个二维数组的名字、地址;而arr[0]是一维数组’‘{1,2,3,4}’'的名字、地址,arr[1]、arr[2]类推
-
-
在C语言中规定了:数组名代表数组首元素地址
-
基于以上认知,可得:&arr[0]与&arr[0][0]是等价的
-
二维数组的偏移
一维数组的偏移是这样的:"*(arr+i)“表示"从第0个元素始,偏移了i个元素”
在二维数组中,我们也可以采用这种思想理解:
-
"*(arr+i)“也表示"从第0个元素始,偏移了i个元素”,不过这里的1个元素代表一个一维数组;
-
“*(arr[0]+i)“表示”**‘从arr[0]这个一维数组的’**第0个元素始,偏移了i个元素”,
-
二 通过编程验证"一"中的认知
- 验证内容:"arr"就是整个二维数组的名字、地址;而arr[0]是一维数组’‘{1,2,3,4}’'的名字、地址
- 代码示例:
#include <stdio.h>
int main()
{
int arr[3][4]=
{
{11,21,31,41},
{51,61,71,81},
{91,101,111,121}
};
int (*p_arr)[4];
p_arr=arr;
int *p_arr2;
p_arr2=arr[1];
int len;
len=sizeof(arr)/sizeof(arr[0][0]);
int i;
printf("验证arr是二维数组的名字、地址:");
for(i=0;i<len;i++)
{
printf("%d;",*(*p_arr+i));
}
printf("\n\n");
printf("验证arr[1]是一维数组{5,6,7,8}的名字、地址:");
for(i=0;i<len/3;i++)
{
printf("%d;",*((p_arr2+0)+i));
}
return 0;
}
- 成果展示:
- 报错与总结:数组里的元素不能是连续的整数,指针使用不规范会造成:不是指针偏移,而是指针所指位置的元素递加,这种情况只有在数组里的元素不是连续时才能在测试中看出来
2.验证内容:
"*(arr+i)“也表示"从第0个元素始,偏移了i个元素”,不过这里的1个元素代表一个一维数组;
“*(arr[0]+i)“表示”**‘从arr[0]这个一维数组的’**第0个元素始,偏移了i个元素”,
- 代码示例:
#include <stdio.h>
int main()
{
int arr[3][4]=
{
{11,21,31,41},
{51,61,71,81},
{91,101,111,121}
};
int (*p_arr)[4];
p_arr=arr;
int *p_arr2;
p_arr2=arr[0];
printf("验证\"*(arr+2)\"表示偏移2个一维数组:");
printf("%d;",**(p_arr+2));
printf("\n\n");
printf("验证\"*(arr[0]+2)\"表示偏移2个元素:");
printf("%d;",*((p_arr2+0)+2));
return 0;
}
- 成果展示:
- 报错与总结:无