我在我的gcc上尝试了这个:
int a=1;
cout<<(--a)--;
,输出为0;但改为
cout<<--(a--);
导致错误(减值操作数需要左值)。有人可以告诉我这个吗?
谢谢!
答案 0 :(得分:12)
++
的两个版本都需要左值作为参数,但前缀版本返回左值作为参数,而后缀版本返回右值。
无论哪种方式,您都无法在序列点之间修改同一对象两次,因此您的“工作”示例会调用undefind行为。输出可以是编译器的感觉。如果你只是出于好奇而好奇,但如果这与你的实际代码有关,你可能会做错事。
答案 1 :(得分:8)
预先递增--a
递减a
,然后返回a
本身。因此,您可以继续以任何方式修改它,包括后递减。
postdecrement a--
递减a
但会在递减之前返回一个值。它本质上是给你a
的副本。但是你不能再预先复制这个副本。它不是左值,所以没有什么可以减少的。这就是为什么这是一个错误。
将predecrement视为返回对a
的引用,并将postdecrement返回为常量值。
答案 2 :(得分:4)
(--a)--
这是未定义的行为,因为您在没有插入序列点的情况下修改同一对象两次。调用UB时,编译器不需要报告 - 在许多情况下, 无法甚至检测到UB。但是如果你打开正确的警告(你应该看看你提供的是什么),有时可能会这样。
--(a--)
前缀递减需要左值,但后缀递减需要返回右值。这是一个错误,与未定义的行为不同,编译器必需报告。