C++ 为什么if(x=+;+;x=+;+;y)起作用,而if(x+;+;&+;y)不起作用?
当我执行此程序时:C++ 为什么if(x=+;+;x=+;+;y)起作用,而if(x+;+;&+;y)不起作用?,c++,operators,C++,Operators,当我执行此程序时: #include<iostream> using namespace std; int main(){ int x=5,y=9; if(++x=y++){ cout<<"Works "<<x; } else{ cout<<"No"; } return 0; } #包括 使用名称空间std; int main(){ int x=5,y=9; 如果(
#include<iostream>
using namespace std;
int main(){
int x=5,y=9;
if(++x=y++){
cout<<"Works "<<x;
}
else{
cout<<"No";
}
return 0;
}
#包括
使用名称空间std;
int main(){
int x=5,y=9;
如果(++x=y++){
不能,因为x++
不是左值
更具体地说,x++
递增x
,然后返回一个初始值为x
的临时对象。临时对象不能(撇开可疑合法性不谈)在赋值的左侧使用,因此它不是左值
++x
递增x
并返回对x
的引用(及其新值)。然后,如果选择,可以直接分配给它,因此它是左值
但是,您可能实际上是想比较这两个表达式是否相等,而不是进行赋值。在这种情况下,您需要使用=
而不是=
x++返回x,然后递增x。另一方面,++x递增x,然后返回它
第二种情况是有意义的;x正在被返回,您可以做任何事情。第一种情况毫无意义;x++不是一个值。事实上,一旦您返回该值,x就不再是该值。您必须记住,后缀递增运算符在递增之前返回旧值
该值是一个非常临时的值,与所有其他临时值一样,它不是“左值”,也就是说,它不是可以赋值的对象
前缀递增运算符执行递增操作,然后返回对新值的引用。对于++x
,它返回对x
的引用。它是一个“左值”
减量(--
)运算符当然也是如此
互联网上有很多资料可以帮助您理解“左值”和“右值”(临时值)之间的区别。根据运算符优先级添加一些括号,以了解发生了什么:
(++x) = (y++)
这将递增x,递增y,并将y-1(递增之前的y值)赋给x(y++计算为y,因为这里是后递增)
这里的语句无效,因为x++没有左值
参见:
< P>正如大家所解释的,x++< /Cord>的值是一个临时的包含“代码> x/CODE”的旧值,并且临时赋值不能被分配给它。编译器因此拒绝代码,而不符合C++的语法。
您遇到的问题是第一个示例也是错误的。虽然++x
在语法上是一个左值,但如果您将它放在赋值运算符的左侧,您将同时递增x
并赋值给x
,并且不清楚您的意思是什么。C++89和C都有序列点的概念s、 如果在没有插入序列点的情况下修改同一变量两次,则程序的行为不会被定义(任何情况都可能发生,包括用return
或segfault替换整个函数)
C++11引入了一个我不熟悉的不同术语,但在本例中的效果是相同的-您的第一个示例是未定义的行为。@BoBTFish因此,++x
是左值吗?奇怪的是,用于比较的运算符是=
而不是=
。因此很难理解您试图实现的目标。That说,这是一个有趣的问题,++x
是一个左值,但是如果你给它赋值,你会调用未定义的行为(在C和C++89语言中,两个修改没有插入序列点),因为(x++和++y)不属于同一类型,您需要==进行比较。您应该删除if
s,因为它们会让每个人都感到困惑。我是否遗漏了什么?第一个示例怎么不是UB?@MartinBonner如果是例如++x=x++
则是UB。但现在OP使用了两个不同的变量,所以没问题。为什么?T这是x的增量,这是x的赋值。这是两个修改,没有中间的序列点(或者C++11以后的等价术语)@MartinBonner这里是一个关于正常的问题。递增运算符的优先级比赋值高很多,因此将首先执行。前缀递增运算符返回对递增的x
的引用,此引用通常可以用作赋值的左侧。不,这绝对是错误的。o运算符优先级定义正在操作的对象(例如a/b+c
意味着/
的操作数是a
和b
,而不是b+c
),而不是副作用的顺序。我必须在回答中查找措辞并引用相关部分。
(++x) = (y++)
(x++)=(y++)