三元条件和赋值运算符优先级

时间:2011-09-21 12:02:22

标签: c++ operator-precedence conditional-operator

我对直接赋值和三元条件运算符优先级感到困惑:

#include<stdio.h>
int main(void)
{
    int j, k;

    j = k = 0;
    (1 ? j : k) = 1; // first
    printf("%d %d\n", j, k);

    j = k = 0;
    1 ? j : k = 1; // second
    printf("%d %d\n", j, k);
    return 0;
}

我希望输出为:

1 0
1 0

但恰好是:

1 0
0 0

另外我收到此警告:

  

main.cpp:20:警告:声明无效

这是我评论的第二行。

由于直接赋值运算符的优先级低于三元条件运算符,因此我期望第一行和第二行的注释等效。但实际情况并非如此。

我试着使用g ++ --version(Ubuntu 4.4.3-4ubuntu5)4.4.3

4 个答案:

答案 0 :(得分:20)

C / C ++语言中的运算符优先级未由表或数字定义,而是由语法定义。以下是来自C++0x draft 5.16条件运算符[expr.cond] 的条件运算符的语法:

conditional-expression:
    logical-or-expression
    logical-or-expression ? expression : assignment-expression

因此,当您在doublecolon的左侧使用赋值时,this one之类的优先表是正确的,但在右侧使用时则不然。我不知道这种不对称的原因是什么。这可能是一个历史原因:在C中,条件结果不是左值,因此为它分配一些东西是没有意义的,并且允许在没有括号的情况下接受赋值可能在那时看起来很聪明。

答案 1 :(得分:14)

第二行相当于:

1 ? (j) : (k = 1);

这与:

相同
j;

这与:

相同
;

关键是三元条件运算符的两个操作数可以是表达式,因此运算符优先级在这里不相关。只是第二个操作数是赋值表达式k = 1

答案 2 :(得分:8)

(1 ? j : k) = 1;

相当于,

if(true) j = 1;
else k = 1;

1 ? j : k = 1;

相当于,

if(true) j;  // warning: statement has no effect
else k = 1;

答案 3 :(得分:3)

在第二种情况下,

1 ? j : k = 1;

评估为:

(1) ? (j) : (k = 1);

并且由于一个求值为true,因此表达式求值为j,它不执行任何操作。