三元运算符的奇怪枚举行为

时间:2014-06-30 13:57:58

标签: c enums

我正在用一个我的枚举编写一个非常简单的三元运算符,我偶然发现了一个非常奇怪的错误(对我来说......)。鉴于这段代码:

typedef enum
{
    first = 0,
    second,
    last
}myEnum;

myEnum myVar = first;

(myVar < second) ? myVar++ : myVar = last;

编译器发给我以下错误:

  

错误:左值作为赋值的左操作数

好像我只是将三元组更改为if / else块,如下所示:

if(myVar < second)
{
    myVar++;
}
else
{
    myVar = last;
}

一切都可以编译并正常工作。有人可以解释为什么写成三元组的完全相同的代码无法编译?我错过了什么?

2 个答案:

答案 0 :(得分:5)

您的表达式被解析为:

( (myVar < second) ? myVar++ : myVar ) = last;

但您似乎打算这样做:

(myVar < second) ? myVar++ : (myVar = last);

这实际上并不完全符合标准的要求(但许多编译器以这种方式解析),第一个表达式实际上应该因为另一个原因而失败(语法错误而不是约束违规)。

C99 6.5.15说:

conditional-expression:
    logical-OR-expression
    logical-OR-expression ? expression : conditional-expression

myVar = last不是条件表达式,而是赋值表达式(C99 6.5.16):

assignment-expression:
    conditional-expression
    unary-expression assignment-operator assignment-expression

但是(myVar < second) ? myVar++ : myVar不是一元表达式(参见C99 6.5.3)(但其括号内的版本将是,就像我在第一个代码片段中写的那样,请参阅C99 6.5.1)。

HTH

答案 1 :(得分:2)

你所做的和你想做的事情是无法比较的。

这一个

if(myVar < second)
{
    myVar++;
}
else
{
    myVar = last;
}

转换为

myVar = (myvar < second) ? myvar + 1 : last;

如果你想完全建立副作用,你也可以

(myVar < second) ? myVar++ : (myVar = last);

但我不确定这是好的风格,因为它可能会使读者对表达的意图感到困惑。