错误:在这个简单的C代码中需要左值吗? (三元分配?)
我有 :
#include<stdio.h> int main() { int a=5,b=6; (a>b)?b=a:b=b; // Here is the error return 0; }
但是如果我replace:
(a>b)?b=a:b=b; // Error with (a>b)?(b=a):(b=b); // No-Error
我知道lvalue
是可以赋值的rvalue
,它与rvalue
有什么不同,但为什么extra parenthesis
产生差异。
赋值比三元运算符具有更低的优先级,因此该行的计算结果如下所示:
((a>b)?b=a:b)=b;
使用:
b=(a>b)?a:b;
实际上,在C中,这个代码
(a>b)?b=a:b=b;
被许多编译器parsing为
((a>b)?b=a:b)=b;
这是一个错误,因为expression式((a>b)?b=a:b)
计算结果是一个右值 ,你试图用b
来赋值,这会导致错误。 试图分配一个右值是一个错误。 如果不这样parsing,那么它只是一个语法错误。 但是不允许C编译器将其parsing为:
((a>b)?b=a:(b=b)); //not allowed to parse by C language
因为C的语法不允许编译器像上面那样parsing代码。
但是你所写的(原始代码)和C ++一样是正确的。
这里C和C ++的语法差别很大。 而由于这种差异,你会看到两种语言对待expression的方式不同。 也就是说, the conditional expression in C++
中the conditional expression in C
是不同 the conditional expression in C
。
维基百科对此有非常好的正确的解释 :
在C和C ++中,运算符的绑定是由一个因式语言语法指定的(在相应的标准中),而不是一个优先级表。 这造成了一些微妙的冲突。 例如,在C中,条件expression式的语法是:
逻辑或expression式? expression式:conditional-expression
而在C ++中是这样的:
逻辑或expression式? expression式:赋值expression式
因此,expression式:
e = a <d? a ++:a = d
这两种语言的parsing方式不同。 在C中,这个expression式是一个语法错误,但许多编译器将其parsing为:
e =((a <d?a ++:a)= d)
这是一个语义错误,因为条件expression式(可能是一个++)的结果不是一个左值。 在C ++中,它被parsing为:
e =(a <d?a ++:(a = d))
这是一个有效的expression。
这是真的:
((a>b)?b=a:b)=b;
注意:你应该简单
b = (a>b)?a:b;
当我们把一个方程放在括号里时,它被当作一个expression式。 并且它返回一些值来解决错误。