右值引用
1. 基础概念
在C/C++中,表达式可以分为左值和右值。
-
左值(
lvalue):是locator value的缩写,表示了存储在内存中,有明确存储地址(可寻址)的对象。-
左值一般出现在表达式左侧,大部分左值是可以被修改的,但也存在一些不可以被修改的左值,例如被
const修饰的左值。 -
左值也可以作为右值使用,出现在表达式右侧。
int a = 10; int b = a; // a是左值,这里当作右值使用
-
-
右值(
rvalue):是read value的缩写,是可以提供数据值的数据,但是不可取地址-
右值只能出现在表达式的右侧:
int a = 5; 1 = a; // 这里发生错误
-
此外,右值又可以分为两种:
- 纯右值:
- 非引用返回的临时变量。
- 运算表达式产生的临时变量。
- 原始字面量。
lambda表达式
- 将亡值:
- 与右值引用相关的表达式。比如
T&&类型函数的返回值、std::move的返回值等。
- 与右值引用相关的表达式。比如
2. C++11 右值引用
在C++11之前,我们无法为右值建立引用,只能通过&操作符为左值建立左值引用:
int a = 10;
int &b = a;
而在C++11中,建立右值引用被实现,通过&&操作符。通过右值引用的声明,右值将会重获新生,右值的生命周期将变得和右值引用的声明周期一致,只要该右值引用还或者,右值就能一直存活下去。
EG:
#include <iostream>
using namespace std;
int&& value = 520;
class Test
{
public:
Test()
{
cout << "construct: my name is jerry" << endl;
}
Test(const Test& a)
{
cout << "copy construct: my name is tom" << endl;
}
};
Test getObj()
{
return Test();
}
int main()
{
int a1;
int &&a2 = a1; // error
Test& t = getObj(); // error
Test&& t = getObj();
const Test& t = getObj();
return 0;
}
int&& value = 520:520是纯右值,value是对520的右值引用。int &&a2 = a1:a1是一个左值,不能用左值来初始化一个右值引用。Test& t = getObj():getObj函数返回的是一个右值,不能用来给左值引用初始化。Test && t = getObj():此时getObj()返回的临时对象被称之为将亡值,t是这个将亡值的右值引用。const Test& t = getObj():常量左值是一个万能引用,它可以接受左值、右值、常量左值、常量右值。

浙公网安备 33010602011771号