一、基本概念
本文主要分析右值引用中的:移动语意(move semantics)。
要想理解右值,首先得能够判断具体什么是右值,先来看一些关于右值的判定条件:
一、任何表达式不是左值就是右值,左值和右值只是针对表达式定义的。
这个比较容易理解,int temp = 10, func(), double a = 0.0, x++, ++x, *ptr,x+y这些都是表达式,他们不是左值就是右值。
二、右值的生存期只到表达式结束,即语句的分号之后右值的生存期就结束了。
三、能够对左值取地址,但无法对右值取址。
四、左值能够在赋值表达式的左边和右边,但是右值无法放在赋值表达式的左边。
看完上述定义应该可以对右值有点了解了吧,它是一个只能放在赋值表达式右边的临时值。
为什么要提出右值这么个复杂的概念,原因是很多代码中生成了很多临时变量,在生成临时变量的时候无法避免地增加了分配内存和释放内存的开销(对于内存较大或内存分配频繁时开销很大),这种时候没必要再为左值重新分配内存,只需要把右值中大块内存的指针地址赋值给左值的指针即可。
这种情况类似于浅拷贝(shallow copy),不同之处在于浅拷贝没有把等号右边值的指针变为nullptr,右值(临时变量)在析构的时候将内存释放掉,左值指针指向的内容被释