Reputation: 77
If an xvalue is a value that is at the end of its lifetime, what is a named rvalue reference if not an lvalue or xvalue (because it is not expiring and is movable)?
Upvotes: 0
Views: 200
Reputation: 3682
Read this part carefully:
In C++11, expressions that:
have identity and cannot be moved from are called lvalue expressions;
have identity and can be moved from are called xvalue expressions;
do not have identity and can be moved from are called prvalue ("pure rvalue") expressions;
do not have identity and cannot be moved from are not used[6].
The expressions that have identity are called "glvalue expressions" (glvalue stands for "generalized lvalue"). Both lvalues and xvalues are glvalue expressions.
The expressions that can be moved from are called "rvalue expressions". Both prvalues and xvalues are rvalue expressions.
So this means that a named rvalue reference is an lvalue.
Go to https://en.cppreference.com/w/cpp/language/value_category for more info.
According to the link above, one of properties of rvalues is that
Address of an rvalue cannot be taken by built-in address-of operator: &int(), &i++[3], &42, and &std::move(x) are invalid.
Now let's look at an example and take advantage of this property:
#include <iostream>
void getNum( int&& i ) // i is an rvalue reference, meaning that it can
// bind to both xvalues and prvalues
{
std::cout << "i: " << i << " --- Address: " << &i << '\n'; // notice how the
// & operator works for i
i += 50;
std::cout << "i: " << i << " --- Address: " << &i << '\n'; // also here
}
int main()
{
getNum( 35 ); // in this case, we pass it a prvalue
std::cout << '\n';
int number { 23 }; // number is an lvalue
getNum( std::move( number ) ); // and in this case we pass it an xvalue
// since std::move(number) returns an xvalue
}
The output will be similar to the following:
i: 35 --- Address: 0x4f4b9ff62c
i: 85 --- Address: 0x4f4b9ff62c
i: 23 --- Address: 0x4f4b9ff628
i: 73 --- Address: 0x4f4b9ff628
As you can see, the address of operator& does in fact return the address of i
. This clearly shows that a variable of type rvalue reference T&&
is an lvalue.
Upvotes: 2