数组与指针的关系

前言

此博客参考借鉴了《C Traps and Pitfalls》

正文

1.对于任何一个数组我们可以确定数组的大小,获取指向该数组下标为0的元素的指针。这实际上都是通过指针进行的。换句话说我们可以通过指针的行为定义数组下标的行为。

1.数组的声明

stcuct
{
 int p[4];
 double x;
}b[17];

这里声明了b是一个拥有17个元素的数组,其中每一个元素是一个结构体,每个结构体包括了一个拥有4个整形元素的数组,和一个double类型变量。

int calendar[12][31];

这个语句声明calendar是一个数组,这个数组有12个数组类型的元素,每一个元素都是一个拥有31个整形元素的数组。

所以如果calendar不是sizeof的操作数,而是用于其他场合,那么calendar会被转化成一个指向calendar数组起始元素的指针

2.指针

如果一个指针指向的是数组中的元素,那么我们给指针+1就可以指向数组下一个元素,同理-1类似。

由此可知给指针+/-一个整数,表示为指向计算机内存的下一个整数

所以我们可以得出:

如果指针指向的是同一个数组的元素,两个指针相减可以得出中间的元素个数。

在这里插入图片描述

注意:如果两个指针指向的不是同一块空间,则两个指针相减没有任何
意义,是一个随机值。

3.数组名与&数组名

声明int a[10]={0}; int* p;

p=a;数组名会被当成指向该数组下标为0的元素的指针。

p2=&a这表明取出的是数组整个的地址,p+1会跳过整个数组,但p2与p的值相同,都是数组首元素的地址。

注意:p2=&a在严格意义上是非法的,因为&a是一个指向数组的指针,而p2是一个指向整形变量的指针,他们的类型不匹配。

4.a[i]=*(a+i)

定义a是整型数组。
*a=80表示将数组的首个整形元素大小改为80。由此可以类比
*(a+i)表示数组下标为i的元素简记为a[i]

再考虑二维数组
声明

int calendar[12][31];
int* p;
int i;

calendar数组有12个元素。每个元素是一个有31个整形元素的数组,所以
calendar[4]表示calendar第5个元素,是一个数组。因此calendar与一个有31个整形元素的数组的性质相类似。

eg:sizeof(calendar[4])=31*sizeof(int);

由上可知:
在这里插入图片描述
再看:p=calendar;
这句话是非法的因为calendar名称会转化成一个指向数组的指针,但是p是一个指向整形元素的指针,类型不匹配。

所以要想上式成立p的定义要改为
int(*p)[31]这表明了p是指针,指向了一个含有31个整形元素的数组。

结尾

所以下面代码

int month;
for(mouth=0;mouth<12;mouth++)
{
  int day=0;
   for(day=0;day<31;day++)
   {
      calendar[month][day]=0;  
   }
}

可以用指针写成

int(*month)[31];
for(month=calendar;month<&calendar[12];month++)
{
 int* day;
 for(day=*month;day<&(*month)[31];day++)
 {
 *day=0;
 }
}

由上面可以看出,用a[i]来表示*(a+i)更方便。但上面的式子对于我们更好的理解数组与指针有帮助。

此博客参考了《C Traps and Pitfalls》,有什么问题欢迎指正

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

NUC_Dodamce

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值