Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does binding to const reference from a ternary make a copy? [duplicate]

Tags:

c++

I am baffled by this:

#include <iostream>
struct X {};
void f( const X &x ) { std::cerr << &x << "\n"; }

static X x;
int main()
{
  f( x ); // Off stack address
  f( false ? X() : x ); // Different address on stack.
}

Why would the second invocation of f make a temporary copy?

Edit: This question is not so much about the type X, but the fact that a copy is made. I was missing the sublety of value categories from the accepted answer and had expected f's parameter to bind on either x or X() directly like it does when rephrasing this as an if statement.

like image 308
bking Avatar asked May 06 '15 21:05

bking


1 Answers

The conditional operator determines a common type and value category for its second and third operands. Whichever branch is chosen (as determined by the condition), the corresponding operand is converted into this common type and value category.

In this case X() and x both have type X, so the common type is of course X itself. But the result is a prvalue, so if x is chosen (the condition is false) then the lvalue-to-rvalue conversion is applied, creating a prvalue temporary copy of x which is then bound to the reference.

In conclusion, the use of the conditional operator itself is what forces the copy to be made.

like image 100
Brian Bi Avatar answered Sep 22 '22 19:09

Brian Bi