首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >问答首页 >为什么*pp[0]等于**pp

为什么*pp[0]等于**pp
EN

Stack Overflow用户
提问于 2016-01-27 07:39:03
回答 3查看 1.4K关注 0票数 3

所以我试图弄清楚指针,我读了一些关于指针的文章,但我仍然不明白为什么这个程序运行起来没有问题

代码语言:javascript
代码运行次数:0
运行
复制
#include <stdio.h>
#include <assert.h>

int main(){
    char* p = "abc";

    char** pp[2];
    pp[0] = &p;
    assert(*pp[0]==**pp);

    printf("Comparison: %s, %s\n",**pp, *pp[0]);

    return 0;
}

据我所知,记忆应该是这样的

代码语言:javascript
代码运行次数:0
运行
复制
Memory Address (hex)    Variable name    Contents
1000                                     'a' == 97 (ASCII)
1001                                     'b' == 98
1002                                     'c' == 99
1003                                     0
...
2000-2003               p                1000 hex
...
3000-3003               pp[0]            2000 hex

在这一点上,假设我的记忆是正确的…我希望*pp进入内存并说...

所以pp指向p的地址,它是0x2000,通过取消引用,我希望获得地址0x2000的内容,在我看来,这意味着我将获得0x1000,但情况并非如此,因为程序的输出是:

输出

代码语言:javascript
代码运行次数:0
运行
复制
abc, abc

在**pp的情况下,我认为它首先解引用pp,这将给我们提供pp所指向的内容,这意味着0x2000 (即0x1000)的内容,然后通过再次解引用,我们得到地址0x1000的内容

为什么它们是相等的呢?我遗漏了什么吗?

EN

回答 3

Stack Overflow用户

发布于 2016-01-27 07:44:46

在大多数上下文中,如果您有一个数组a,则a&a[0]的缩写。(也有一些例外,例如sizeof a&a)。

所以**pp实际上是指**&pp[0]

&pp[0]pp[0]的地址,所以*&pp[0]等同于pp[0],所以**&pp[0]等同于*pp[0]

票数 5
EN

Stack Overflow用户

发布于 2016-01-27 07:49:02

pp总是和*pp一样,不管你处理的是什么类型的指针。

鉴于方括号的运算符优先级很高,*pp与*(pp)相同...根据上面的句子,它将与*(*pp)相同,后者与**pp相同。Q.E.D.

票数 2
EN

Stack Overflow用户

发布于 2016-01-27 07:50:19

,所以pp指向p的地址,它是0x2000,通过取消引用,我希望得到地址0x2000的内容

这是你的推理失误,但可以理解。在C中,赋值的右边,或者通常是对左值的求值,更准确地说,是左值到右值的转换,已经是一个解引用了!例如,int i, j=0; i=j;有效地取消了对j的引用;j是一个地址常量,赋值涉及存储在那里的值,j的值,因此赋值等于i=0。其他语言,如Algol68,更精确:一种语言可以有效地编写int i; int *pi = i;,这是完全有意义的(pi现在指向i)。

这就是为什么在使用*pp[0]显式地取消对pp[0]的引用时,实际上是在两次取消对它的引用:首先查看地址0x2000的内容,即0x1000,然后再取消引用以便在0x1000处读取内存。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35026135

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档