提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
文章目录
一、左值😊右值
一般来说,允许其内存写入的(a)是左值,没办法对其内存写入的,例如(1+2)是右值。左值(一般是=左边)a有着明确的内存空间 例如1+2(一般在等号右边)这样没用变量指示内存的称为右值。
主要区别如下
左值(lvalue):
左值是指表达式结束后仍然存在的对象,它们具有持久性。
左值可以出现在赋值语句的左边或右边。
左值可以取地址,可以被引用,可以被修改。
通常是具名的变量、数组元素、引用等。
右值(rvalue):
右值是指表达式结束后就消失的临时对象,它们是短暂的。
右值不能出现在赋值语句的左边。
右值不能取地址,通常不能被修改。
通常是字面值常量(1)、临时对象、函数返回值(返回类型为一个单纯的int,或者对象类型)等。
在C++中,当函数返回一个局部变量时,实际上返回的是该局部变量的右值。右值是指不能被取地址的临时对象,通常是表达式的结果或临时变量。在这种情况下,编译器会将局部变量的值移动到函数调用点的目标位置,然后销毁该局部变量。
二、左值引用和右值引用
2.1左值引用(Lvalue Reference):
引用本质是别名,可以通过引用修改变量的值,传参时传引用可以避免拷贝。
左值引用是最常见的引用类型,通过 & 符号声明。
左值引用可以绑定到左值(持久存在的对象),并且可以修改被引用对象的值。
左值引用通常用于函数参数传递和返回左值对象。
int x = 5;
int& ref = x;
2.2右值引用:
通过 && 符号声明。
右值引用可以绑定到右值(临时对象),通常用于支持移动语义。
右值引用通常用于移动语义,允许有效地转移资源的所有权而不进行深拷贝。
int&& b = 10;//右值(别名)b就是对右值10的引用
b = 3;//右值引用允许修改右值
int a = 1;
int &&c= a;// 编译不过,右值引用不可以指向左值
三、int && str =右值 与const int &str = 右值 啥区别
在这两种情况下,都涉及将一个右值绑定到一个引用上,但是它们之间有一些重要的区别:
-
person&& str = 右值
:- 这里的
str
是一个右值引用,可以绑定到一个临时对象(右值)上。 - 右值引用的特性允许移动语义(c++11特性),允许我们将对象的所有权转移到另一个对象,而不进行资源的拷贝操作。不保留原来的对象资源。
- 在这种情况下,
str
将直接绑定到右值,并且可以在后续操作中使用移动语义来提高性能。
- 这里的
-
const person& str = 右值
:- 这里的
str
是一个const
左值引用,可以绑定到一个右值或左值对象上。 const
修饰符表示引用是只读的,不能修改绑定的对象。- 在这种情况下,
str
虽然可以绑定到右值对象,但由于是一个const
引用,无法修改所绑定对象的内容,也无法利用移动语义来避免对象复制。 - const左值引用不会修改指向值。因此可以指向右值,这也是为什么要使用 const & 作为函数参数的原因之一,如 std::vector 的 push_back 。
- 这里的
void push_back (const value_type& val);
如果没有 const , vec.push_back(5) 这样的代码就无法编译通过。