关于二维数组的指针理解

#include  <stdio.h>  
 int main()  
 {  
     int s[3][3]={{1,2,3},{4,5,6},{7,8,9}};
     int (*ps)[3][3] ={&s};
     printf("value:%x\n",ps[0][0]);  /*0x22fe20存着s的地址*/
     printf("value:%d\n",*ps[0][0]);  /*1 首元素的内容*/

     printf("value:%d\n",s[0][0]); /*1 首元素的内容*/ 
     printf("addr:%p\n",s);  /*0x22fe20 s的地址*/
 }
     printf("value:%x\n",ps[0][1]);  /*0x22fe2c,即首地址+12*/
     printf("value:%d\n",*ps[0][1]);  /*4*/
     printf("value:%x\n",ps[1][0]);  /*0x22fe44,即首地址+36*/
     printf("value:%d\n",*ps[1][0]);  /*0*/

int (*ps)[3][3]定义的是一个指针,指针指向一个3*3的数组,实际上,只能通过它读取到s[1],s[2]和s[3],即第1、2、3行内容的首元素。
这是由于s[3][3]本身就是等同于一个s[3],而这三个数组元素中存的内容是int *,也就是各行的首地址。
也就是说,int(*x)[]这种格式,对于二维数组来说,并不适用,只能取到每行的无法直接调用x[][]。
而实际上,若定义int (*ps)[3][3]格式的形参,对于C来说,实际上是把它当做int *(*ps)[3],也就是退化成一个指针,该指针是一个指向指针数组(包含3个元素)的指针。同理,
int *ps[3][3]类型当做形参,也是一样。但由于int *ps[3][3]是3*3的指针数组,在赋值时,如果直接让它等于{&s},只能给ps[0][0]赋值,其他均是初值,只能直接读到整个数组的第一个元素。

若到在C中直接使用二维数组的指针传参,最多只能直接得到各行的首地址,其后的元素地址,需要通过指针操作来获得。

若需要把二维数组传入函数,最简便的方法,是直接传数组本身即可。
此时对于函数来说,传入的二维数组的类型为int (*)[3],即为一个指向3个元素的数组指针(可直接利用下标得到元素,其实本质都是指针,但与直接传递指针不同,起到声明的效果)

#include  <stdio.h>  
void test(int tmp[3][3])
{
     printf("%x\t",tmp); /*22fe20*/
     printf("%d\t",(tmp[1][2]));/*6*/
     (tmp[1][2]) = 2;
     printf("%d\t",(tmp[1][2]));/*2*/
}
 int main()  
 {  
     int s[3][3]={{1,2,3},{4,5,6},{7,8,9}};
     printf("%x\t",s);/*22fe20*/
     test(s);
     printf("%d\t",(s[1][2]));/*2*/
 }

结论:在函数中传入数组,等同于传入指针,对形参的改变,会同时改变实参

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值