在C和C ++中+ =的结果是什么?
我有以下代码:
#include <stdio.h> int main(int argc, char **argv) { int i = 0; (i+=10)+=10; printf("i = %d\n", i); return 0; }
如果我尝试使用gcc将其编译为C源代码,我得到一个错误:
error: lvalue required as left operand of assignment
但是,如果我使用g ++将其编译为C ++源代码,则不会出现错误,并且在运行可执行文件时:
i = 20
为什么不同的行为?
C和C ++中复合赋值运算符的语义不同:
C99标准,6.5.16,第3部分:
赋值运算符将值存储在由左操作数指定的对象中。 赋值expression式在赋值后具有左操作数的值,但不是左值。
在C ++ 5.17.1中:
赋值运算符(=)和复合赋值运算符全部从右到左。 所有这些操作都需要一个可修改的左值作为它们的左操作数,并在赋值发生后返回左操作数的types和值的左值。
编辑: C (i+=10)+=10
的(i+=10)+=10
的行为在C ++ 98中是未定义的,但是在C ++ 11中定义良好。 请参阅NPE关于标准相关部分的问题的答案 。
除了无效的C代码之外
(i+=10)+=10;
会在C和C ++ 03中导致未定义的行为,因为它会在序列点之间修改两次。
至于为什么允许用C ++编译:
[C ++ N3242 5.17.1]赋值运算符(=)和复合赋值运算符全部从右到左。 所有需要一个可修改的左值作为它们的左操作数, 并返回一个指向左操作数的左值。
同一段落继续说
在任何情况下,赋值都是在左右操作数的值计算之后,赋值expression式的值计算之前进行sorting的。
这表明在C ++ 11中,expression式不再具有未定义的行为。