Consider the following class:
class Foo
{
std::string name;
public:
Foo(std::string some_name) : name(std::move(some_name))
{
}
std::string& original_name()
{
return name;
}
std::string copy_of_name() const
{
return name;
}
};
The expression some_foo.copy_of_name()
is a prvalue, because copy_of_name
returns an object (std::string
), not a reference. Every prvalue is also an rvalue. (Rvalues are more general.)
The expression some_foo.original_name()
is an lvalue, because original_name
returns an lvalue reference (std::string&
). Every lvalue is also a glvalue. (Glvalues are more general.)
The expression std::move(some_name)
is an xvalue, because std::move
returns an rvalue reference (std::string&&
). Every xvalue is also both a glvalue and an rvalue.
Note that names for objects and references are always lvalues:
std::string a;
std::string& b;
std::string&& c;
Given the above declarations, the expressions a
, b
and c
are lvalues.
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…