C语言指针和地址,理解*p和**p

在计算机中所有数据都存放在存储器中。

把主存储器中的一个字节称为一个内存单元 ,通过内存单元的编号能正确地访问内存单 元,内存单元的编号也称为地址。

&:取地址运算符。

*: 指针运算符。

int a;  //定义一个整型变量a

&a则可以获取到变量a的地址(编号)

可以想象它是:6422020,或者任意数字,总之它是个编号,是个常量

如果要把a的地址,放到一个变量p存起来,则把a的地址赋给p,即:p = &a

但,有个重要的前提是:定义p是一个指针变量,还得是整型指针变量,因为变量a是整型的

这个是C语言的法则。

如何让p成为一个整型指针变量呢?

可以这么做: int *p;    //在定义p的时候,前面加个*号,这个*号就告诉了编译器任命变量p为一个指针变量,专门用于存放地址的,地址一定是一个常量。而写在更前面的类型说明符 int 则是要求变量p存的这个地址它对应的变量是整型变量

那么如何取到a的值呢?

两种方法:可以用*p,也可以直接用a 来取。*p和a是等价的。听起来有点拗口?用程序+图来说明:

 

6466020是变量a的地址,此时a的“肚子”里有个值是100,变量p的“肚子”里有个值是6422020(&a取出来的a的地址)( 6666666是p的地址,这里没必要画出来,但是觉得画出来比较完整吧)*p这个针是扎进了这个地址对应的变量a的肚子里,取出来的是a的值100。对于*p,教科书上的解释是:p指向了变量a。 我觉得指来指去很难理解,于是我把指针理解成打针的针,一旦某个变量前面加了个*,这个变量就变成了个针筒,比如*p,这个针*p戳到哪,吸出来什么,是由它的变量肚子装的哪个地址决定的,就是往哪戳总要有个目标吧。比如这里的针 *p,  变量p肚子里的地址是6466020,于是它戳进了地址6466020对应变量a的肚子,吸出来了个值:100

简单来讲:*p 就是为了变量p拿到的地址对应内存里的值   (从硬件方向去理解)

简单来讲:*p 就是为了变量p拿到的地址对应变量里的值   (从软件方向去理解)

上面两句话是一个意思,总之硬件上就是一个“肚子”,一个“房间”,一个“空间”,软件上它总得有个名,变量a,b,c 什么的都行 

如果这样定义p : int p,没有*号,那么p肚子里是装不了a的地址的,float *p也不行,float *p 定义后,p只能装float类型的变量的地址,比如以下这样定义才是合法的:

float *p;

float a;

a = 3.14159;

p=&a;

那么如何改变a的值呢?

同理也是两种办法:

a = 5.9999; 

或者 *p = 5.9999

——————————————————————————————————————————

*p总结完了,**p呢?

我为什么把指针的针想象成打针的针,也是因为理解完**p后决定的。

如果定义了**p,那么给p赋值的时候,仍然要求是个地址,而且还得是指针变量的地址不能是其他的值,比如值是整型的100之类的变量的地址是行不通的,不符合法则的

先上一段不符合法则的代码:

代码段①:

int **p;

int a;

a = 100;

p=&a;

第四行这里,编译器是不会通过的。

再上一段符合法则的代码:

代码段②:

int **p,*t;

int a;

a = 100;

t = &a;

p=&t;

**p  我认为可以按套娃的模式来理解了:

如果是定义的是int *p,只有一个*号,那就只有一针,一针戳到的肯定是整型变量的地址,不可能戳到的是其他类型的,因为*p要吸出来的值肯定得是个整型。

如果定义的是int **p,有两个*号,那用**p取值的时候就得是两针,一针下去戳到的得是整型指针变量的肚子,图上的变量t就是个整型指针变量,如果是别的类型的地址,则不合法,所以代码段①这里把&a直接给到p的话编译器不会通过,因为第二针都还没打,戳一针就到头了。代码段②里把整型指针变量的地址给到p才是正确的p=&t; 这个语句,使得*p一针戳到整型指针变量t的肚子里,吸出了个变量a的地址4444444, 使得**p这第二针下去戳到了变量a的肚子,吸出来值100,  还有,*t也是可以吸出100的

**p *(*p)是等价的,毕竟是从右到左的运算规则,不管定义了*p  和  **p,在给p赋值的时候都得给的是地址,只不过定义*p的话一针就要到头了,而定义**p是需要两针才到头 ,多少*就戳多少针,最后一针吸出来的值类型要和定义时的类型说明符一致。

定义int **p ,*p一针取出来的是地址,**p两针后取出来的就得是int类型的值。

定义int *p,那么*p一针取出来的就得是int类型的值,没有**p,因为没有两针,预约的是一针。

 

 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

Riven_h

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

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

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

打赏作者

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

抵扣说明:

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

余额充值