The difference between returning a reference to a constant and a reference to rvalue

If I'm not mistaken, I think that a constant reference and an rvalue reference can bind to an rvalue. Is there any practical difference between a function that returns the former and a function that returns the last?

EDIT. I cannot change the first, but why am I interested in changing the value of rvalue? Does it make sense?

+7
source share
2 answers

A const lvalue reference can bind to everything. An rvalue reference can only be bound to values โ€‹โ€‹not const r.

  non-const lvalue const lvalue non-const rvalue const rvalue const T& yes yes yes yes T&& no no yes no 

As you can see, they are very different.

Also, if a function call returns an lvalue reference, this expression is an lvalue, but if a function call returns a reference to an rvalue object, this expression is an x โ€‹โ€‹value.

A function call is an lvalue value if the result type is a lvalue reference type or an rvalue reference for a function type, xvalue if the result type is an rvalue reference for an object type and otherwise prvalue.

As for when you want to change the rvalue - well, thatโ€™s exactly what the movement semantics are. Consider the following function call:

 void func(std::string); func(std::string("Hello")); 

The expression std::string("Hello") is an r-value that creates a temporary object. When the std::string parameter is initialized with this rvalue value, it will select the constructor that accepts the rvalue reference, the move constructor. This constructor then stole things from an rvalue, which is usually much faster than a full copy. We can steal from him because we know this is temporary.

As for when you should return const lvalue links or rvalue links:

  • Returning a const lvalue link is most often used when you want to grant read access to an "internal" object (perhaps a member of a class), but don't let people change it.

  • Returning a rvalue reference is most often used (not at all common) when you want to allow code to be called to go from an "internal" object (possibly to a class). Therefore, instead of moving from a temporary returned object (as with a return by value), they literally move from the internal object.

    This can also be achieved using the const lvalue reference, but then they must explicitly specify std::move .

Therefore, it is not very likely that you need to return the rvalue link.

Not that std::forward has a return type that looks like T&& . However, this is misleading because it may or may not be an rvalue reference depending on the type of T See universal links .

+16
source

Is there any practical difference between a function that returns the former and a function that returns the last?

The question seems to be poorly formed. The function that returns the lvalue-reference constant provides read-only access to the object, while the function that returns the rvalue reference provides move access, which means that the caller can take the contents of the mentioned object and move it to another object. They are not comparable by any means.

In both cases, the links must point to an object whose life time extends beyond the function that returns it, because otherwise the caller will travel using undefined when using this link.

+1
source

All Articles