Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

When is an rvalue evaluated?

So I understand that s2 binds to the expression s1 + s1, but is this evaluated at the time s2 is assigned or is it lazy and evaluated when s2 += "Test"; is called? And also would s2 hold memory for a temporary string?

#include <iostream>
#include <string>

int main()
{
    std::string s1 = "Test";
    std::string&& s2 = s1 + s1;
    s2 += "Test";
    std::cout << s2 << '\n';
}
like image 716
Brady Dean Avatar asked Jun 01 '17 04:06

Brady Dean


People also ask

What is the difference between an L value and R value?

An lvalue refers to an object that persists beyond a single expression. An rvalue is a temporary value that does not persist beyond the expression that uses it.

What is R value C++?

An rvalue is an expression that is not an lvalue. Examples of rvalues include literals, the results of most operators, and function calls that return nonreferences. An rvalue does not necessarily have any storage associated with it.

Where is rvalue stored?

Typically, it will be treated like an automatic variable, stored in registers or in the function's stack frame.

Can you take the address of an rvalue?

2) non-modifiable lvalues, which are const. rvalue — The expression that refers to a disposable temporary object so they can't be manipulated at the place they are created and are soon to be destroyed. An address can not be taken of rvalues. An rvalue has no name as its a temporary value.


2 Answers

s2 binds to the expression s1 + s1, but is this evaluated at the time s2 is assigned

Yes.

And also would s2 hold memory for a temporary string?

Precisely, s2 is bound to a temporary std::string.

s1 + s1 will produce a temporary std::string, which will be bound to the reference s2 (and its lifetime is extended to the lifetime of the reference). Then s2 += "Test";, performs operator+=() on s2, i.e. the temporary std::string.

like image 101
songyuanyao Avatar answered Oct 21 '22 00:10

songyuanyao


Expressions are always evaluated at the point the program reaches them. The result of an expression is always a value (or void).

Values have a type, and expressions have a value category, which combine to choose which overload of an overload set is used, at any particular use.

In your case, string operator+(...) results in a string value, with the category pr-value (which is a type of rvalue). It is then immediately bound to a string&&, so it's lifetime is extended to that of the reference.

If you had instead assigned it to a plain string, string& string::operator=(string&&) would have been chosen over any other overloads of that operator. Note that since c++11 the compiler is allowed (and from c++17 required) to materialize the value directly inside the target object. This process is known as copy/move elision or (N)RVO, for (Named) Return Value Optimisation.

like image 31
Caleth Avatar answered Oct 21 '22 02:10

Caleth