小编Osi*_*ris的帖子

*运算符的行为和后跟*运算符

我有一个关于address-of运算符后跟dereference运算符的行为的问题.

让我们来看看表达&*p其中p的类型的int *.

C11标准(第6.5.3.2节)说:

一元&运算符产生其操作数的地址.如果操作数具有类型''type'',则结果具有类型''指向类型''的指针.如果操作数是一元*运算符的结果,则不会对该运算符和&运算符进行求值,结果就好像两者都被省略,除了对运算符的约束仍然适用且结果不是左值.

随脚注:

因此,&*E等效于E(即使E是空指针),并且&(E1 [E2])等于((E1)+(E2)).如果E是函数指示符或左值是一元&运算符的有效操作数,则总是如此,*&E是函数指示符或等于E的左值.如果*P是左值,则T是名称对象指针类型,*(T)P是左值,其类型与T指向的类型兼容.在由一元*运算符解除引用指针的无效值中,有一个空指针,一个与指向的对象类型不适当对齐的地址,以及一个对象在其生命周期结束后的地址.

很明显,除了不是左值之外,&*p必须等于.p&*p

如果我们现在考虑a类型int[10],是什么类型&*a?并且应该在例如sizeof a和sizeof &*a?之间有区别吗?

一方面,如果我们进行评估&*a,a将int *使用解除引用运算符衰减它将变为int并且与地址运算符然后int *.

另一方面,如果&*a表现"好像两个都被省略",那么类型应该是int[10].

一个简短的例子表明gcc将表达式视为不同:

#include <stdio.h>

int main(void)
{
    int a[10];

    printf("%zu\n%zu\n", sizeof a, sizeof &*a);

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

输出:

40
8
Run Code Online (Sandbox Code Playgroud)

这是否符合C11标准?

也许是因为"对运算符的约束仍然适用"而且解除引用运算符的操作数必须是指针?

c language-lawyer

15
推荐指数
1
解决办法
470
查看次数

标签 统计

c ×1

language-lawyer ×1