c++11之左值引用和右值引用
2017-04-07 09:57
381 查看
c++11中增加了右值引用和move语义来避免一些不必要的构造和copy操作,以此来提升程序的运行效率。首先说左值和右值,他们绝不是简单的等号左边和右边的区别,总结来说:
1 .左值可以寻址,而右值不可以。
2 .左值可以被赋值,右值不可以被赋值,可以用来给左值赋值。
3 左值可变,右值可变(仅对基础类型适用,用户自定义类型右值引用可以通过成员函数改变)。
例:int a = 1;左值a可以被寻值,右值1不可以 ,左值a可以被赋值,1不可以,a可变1不可变,int a = b + c,同理a左值,b+c右值。最后c++11中还有一个将亡值的概念,是c++11中新增的跟右值引用相关的表达式,这样的表达式通常是将要被移动的对象。其实标准库中有三个函数帮我们判断引用,左值引用和右值引用:
std::is_rvalue_reference<class _Tp>::value,std::is_lvalue_reference<<class _Tp>>::value,std::is_reference<class _Tp>::value
左值引用就是对左值的引用类型,用T & a来表示,右值引用是对右值的引用类型,用T &&a来表示,左值引用和右值引用同为引用,他们在声明的同时必须被初始化。他们的初始化绑定有一定的规则和限制,例如一个非常量左值引用不能绑定一个常量左值。具体规则如下:
这里我们可以看到常量左值引用是可以绑定右值的,其实这在c98中已经存在,只是我们平时没有留意这个细节而已,例如const int&a = 1等,那么他和const int a = 1,有什么不同呢,从语法上讲后者的右值在表达时结束后就销毁了,而前者不会。这就是我们尽量用const
引用代替值传递做函数参数的原因,它在某种程度上可以提高效率。
那么右值引用有什么用呢?看一个例子。T&& a = ReturnValue(); 当我们调用一个返回一个右值的函数时,当函数返回后,函数返回的右值生命周期也就结束了,但是当我们通过一个右值引用来接收时,该右值有重新获生命,只要我们的右值引用a存在,该右值也同时存在,这又有什么用呢,当我们使用T
a = ReturnValue();这样的方式来接收时,会多一次对象的析构和构造,首先用函数返回值构造b,然后函数返回值生命期结束析构。而右值引用则不会,因为右值引用直接绑定了函数返回的右值。
总结生面两段话,左值引用和右值引用座位函数参数都能避免对象的拷贝和构造,但是我们通过右值引用改变一个右值时是没有意义的,而我们通过左值引用改变一个左值是有意义的。
1 .左值可以寻址,而右值不可以。
2 .左值可以被赋值,右值不可以被赋值,可以用来给左值赋值。
3 左值可变,右值可变(仅对基础类型适用,用户自定义类型右值引用可以通过成员函数改变)。
例:int a = 1;左值a可以被寻值,右值1不可以 ,左值a可以被赋值,1不可以,a可变1不可变,int a = b + c,同理a左值,b+c右值。最后c++11中还有一个将亡值的概念,是c++11中新增的跟右值引用相关的表达式,这样的表达式通常是将要被移动的对象。其实标准库中有三个函数帮我们判断引用,左值引用和右值引用:
std::is_rvalue_reference<class _Tp>::value,std::is_lvalue_reference<<class _Tp>>::value,std::is_reference<class _Tp>::value
左值引用就是对左值的引用类型,用T & a来表示,右值引用是对右值的引用类型,用T &&a来表示,左值引用和右值引用同为引用,他们在声明的同时必须被初始化。他们的初始化绑定有一定的规则和限制,例如一个非常量左值引用不能绑定一个常量左值。具体规则如下:
这里我们可以看到常量左值引用是可以绑定右值的,其实这在c98中已经存在,只是我们平时没有留意这个细节而已,例如const int&a = 1等,那么他和const int a = 1,有什么不同呢,从语法上讲后者的右值在表达时结束后就销毁了,而前者不会。这就是我们尽量用const
引用代替值传递做函数参数的原因,它在某种程度上可以提高效率。
那么右值引用有什么用呢?看一个例子。T&& a = ReturnValue(); 当我们调用一个返回一个右值的函数时,当函数返回后,函数返回的右值生命周期也就结束了,但是当我们通过一个右值引用来接收时,该右值有重新获生命,只要我们的右值引用a存在,该右值也同时存在,这又有什么用呢,当我们使用T
a = ReturnValue();这样的方式来接收时,会多一次对象的析构和构造,首先用函数返回值构造b,然后函数返回值生命期结束析构。而右值引用则不会,因为右值引用直接绑定了函数返回的右值。
总结生面两段话,左值引用和右值引用座位函数参数都能避免对象的拷贝和构造,但是我们通过右值引用改变一个右值时是没有意义的,而我们通过左值引用改变一个左值是有意义的。
相关文章推荐
- C++ 左值引用和右值引用(C++11特性)
- C++11之右值引用(一):从左值右值到右值引用
- C++11 右值引用左值引用详解
- [转]C++11 左值、右值、右值引用详解
- C++11之右值引用(一):从左值右值到右值引用
- C++11 左值、右值、右值引用
- c++11 左值 右值引用
- c++11 左值引用、右值引用
- C++11中,&表示左值引用,&&表示右值引用
- [C++11]左值、右值、左值引用、右值引用小结
- 左值与右值,左值引用与右值引用(C++11)
- C++11 左值、右值、右值引用详解
- [C++11]_[0基础]_[左值引用声明和右值引用声明]
- C++11之右值引用(一):从左值右值到右值引用
- C++11的右值引用(一)——左值(lvalue),纯右值(prvalue)和将亡值(xvalue)
- C++11 左值、右值、引用详解
- C++11 左值、右值、右值引用详解
- 左值、右值与右值引用 & C++11中
- C++11 左值、右值、右值引用详解
- [C++11]_[初级]_[左值引用声明和右值引用声明]