Why does the first conditional operator result in a reference?
int x = 1;
int y = 2;
(x > y ? x : y) = 100;
However, the second does not.
int x = 1;
long y = 2;
(x > y ? x : y) = 100;
Actually, the second does not compile at all:
error: lvalue required as left operand of assignment | (x > y ? x : y) = 100; | ~~~~~~~^~~~~~~~
Expressions don't have return types, they have a type and - as it's known since the C++11 standard - a value category.
A conditional expression can be an lvalue or an rvalue. This is its value category. (This is somewhat of a simplification, in C++11
we have lvalues, xvalues and prvalues.)
In very broad and simple terms, an lvalue refers to an object in memory and an rvalue is just a value that may not necessarily be attached to an object in memory.
An assignment expression assigns a value to an object so the thing being assigned to must be an lvalue.
For a conditional expression (?:
) to be an lvalue (again, in broad and simple terms), the second and third operands must be lvalues of the same type. This is because the type and value category of a conditional expression is determined at compile time and must be appropriate whether or not the condition is true. If one of the operands must be converted to a different type to match the other then the conditional expression cannot be an lvalue as the result of this conversion would not be an lvalue.
ISO/IEC 14882:2011 references:
3.10 [basic.lval] Lvalues and rvalues (about value categories)
5.15 [expr.cond] Conditional operator (rules for what type and value category a conditional expression has)
5.17 [expr.ass] Assignment and compound assignment operators (requirement that the l.h.s. of an assignment must be a modifiable lvalue)