Search code examples
c++c++11rvalue-referenceauto

auto && outside range-for


Am I right in assuming that writing

auto && x = ...;

almost never makes sense outside the for (...) part of a range for, since if the right-hand side indeed is an rvalue, it will normally stop to exist at the semicolon and then x refers to something that has been destroyed.

In other words:

Widget f () { ... }
...
auto && x = f();
// do something with x

is wrong?


Solution

  • From the standard [class.temporary]:

    There are two contexts in which temporaries are destroyed at a different point than the end of the full-expression. The first context is when a default constructor is called to initialize an element of an array.

    The second context is when a reference is bound to a temporary. The temporary to which the reference is bound or the temporary that is the complete object of a subobject to which the reference is bound persists for the lifetime of the reference except:
    — A temporary object bound to a reference parameter in a function call (5.2.2) persists until the completion of the full-expression containing the call.
    — The lifetime of a temporary bound to the returned value in a function return statement (6.6.3) is not extended; the temporary is destroyed at the end of the full-expression in the return statement.
    — A temporary bound to a reference in a new-initializer (5.3.4) persists until the completion of the full-expression containing the new-initializer.

    The line auto&& x = f(); falls into that second context, and none of the exceptions apply. Thus, the temporary persists for the lifetime of the reference. So there's nothing wrong with that code.