Why can braced-init-list not be used in ternary operator?

余生颓废 提交于 2020-07-28 08:48:47

问题


My compiler is the latest VC++ 2013 RC.

int f(bool b)
{
    return {}; // OK
    return b ?  1  : { }; // C2059: syntax error : '{'
    return b ?  1  : {0}; // C2059: syntax error : '{'
    return b ? {1} : {0}; // C2059: syntax error : '{'
}

Why can braced-init-list not be used in ternary operator?

Is this behavior defined as ill-formed by the C++ standard, or just a bug of the VC++ compiler?


回答1:


Well, here's what the standard says about the braced-init-list (8.5.3.1):

List-initialization can be used

  • as the initializer in a variable definition (8.5)
  • as the initializer in a new expression (5.3.4)
  • in a return statement (6.6.3)
  • as a function argument (5.2.2)
  • as a subscript (5.2.1)
  • as an argument to a constructor invocation (8.5, 5.2.3)
  • as an initializer for a non-static data member (9.2)
  • in a mem-initializer (12.6.2)
  • on the right-hand side of an assignment (5.17)

Since this doesn't mention the conditional operator, I guess your compiler is right. Also note that the conditional operator expects expressions on the both sides of : (5.16), and as far as I understand, a brace-initializer is not an expression.




回答2:


It's a syntax error. A braced-init-list is not an expression, and it doesn't have a type or value category. braced-init-list is available at various locations in the C++ grammar, and the operands of conditional expression are not one of those locations. Therefore your code fails to even parse.

If you want to do this:

struct T { ... };

T f(bool b)
{
    return b ? {i,j,k} : {x,y};
}

instead you could do this:

T f(bool b)
{
    return b ? T{i,j,k} : T{x,y};
}

and I believe, although this requires a move constructor, it wouldn't use it and RVO would kick in.

Alternatively you could of course do this:

T f(bool b)
{
    if (b)
        return {i,j,k};
    else
        return {x,y};
}

to get all the advantages of list-initialization.



来源:https://stackoverflow.com/questions/18843017/why-can-braced-init-list-not-be-used-in-ternary-operator

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!