取消引用的指针是有效的左值吗?

Posted

技术标签:

【中文标题】取消引用的指针是有效的左值吗?【英文标题】:Is a dereferenced pointer a valid lvalue? 【发布时间】:2011-01-23 12:42:25 【问题描述】:

假设定义:

int i  = 10;
int *p = &i;

为什么 *p 在这里是一个有效的左值:

*p+=10; 

不应该 *p 计算存储在 &i 中的 int 的值,即。 10,因此会产生“非左值”错误?

【问题讨论】:

我不知道你为什么被否决。我认为这是一个很好的问题 我一直认为*pi 的同义词,从未遇到任何混淆。 *p "当用作右值时,计算为存储在 &i 的 int 的值"。但是作为一个左值,它和左值i是一样的。 *p 始终表示“p 指向的位置的内容”。将*p 解释为左值与右值之间的区别在于,当*p 显示为左值时,可以理解其意图是存储到p 指向的位置,而当*p 用作右值时,可以理解其意图是检索p 指向的内存位置的内容 @Kevin - 我对*p 的内心解读是“指针p 的对象”。可能有点罗嗦,但从心理上讲,这会将*p += 10 转换为“指针 p 的对象增加 10”。 【参考方案1】:

左值是指一个区域的表达式 可以操作的存储空间。

*p 就是这样一个表示存储区域的表达式。这与 10+=10; 不同,因为 10 不像变量那样引用存储区域。

【讨论】:

10 是一个表达式。它只是不是左值。【参考方案2】:

我相信您对p 的定义感到困惑。 p其实是一个指向int的指针类型的变量,它的值被初始化为i的地址。

尽管如此,*p 也是一个有效的左值 - 一个存储位置的有效表达式。

【讨论】:

【参考方案3】:

用非常简单的话来说,指针指向一个对象(在一般的非 OOP 意义上),而不是指向该对象的内容。所以是的,取消引用的指针是一个有效的左值。

在非常低级别的术语中。指针只是一个内存地址,取消引用的指针是该地址处的内存。

【讨论】:

【参考方案4】:

不应将*p 评估为存储在&i 的int 值,即。 10,因此会产生“非左值”错误?

简单来说,

* 表示“地址值”。

*p 表示“p 的值给出的地址处的值”。

*p = 10; 表示“将 10 设置为p 的值给出的地址处的值”。

lvalue 是一个表达式,它引用存储在内存中某处的对象。 *p 也是一个表达式,它引用存储在位置 p 的对象。

【讨论】:

【参考方案5】:

C11 6.5.3.2p4:

语义

...

    一元* 运算符表示间接。如果操作数指向一个函数,则结果是一个函数指示符; 如果它指向一个对象,结果是一个左值指定对象。如果操作数的类型为 ''pointer to type'',则结果的类型为 ''type''。如果为指针分配了无效值,则一元 * 运算符的行为未定义

即与

int i  = 10;
int *p = &i;

*p 的结果是一个左值,用于指定对象i

因此*p += 10 有效,因为它是一个左值。

现在,如果在需要对象本身的上下文中使用左值,它将转换为存储在指定对象中的值。这称为左值转换,结果值当然不再是左值 (C11 6.3.2.1p2)。

【讨论】:

以上是关于取消引用的指针是有效的左值吗?的主要内容,如果未能解决你的问题,请参考以下文章

数组是 JavaScript ECMAScript 中的左值吗?

c++中的左值和右值,右值引用到底是啥?关于引用这一节看得很迷糊。

C++11 中的左值引用和右值引用的区别

在 sizeof 操作中取消引用空指针是不是有效[重复]

指向函数指针的指针 - 表达式必须是可修改的左值

XMM 寄存器中的取消引用指针(收集)