右值引用和移动语义

本文内容:

  1. 什么是右值引用,与左值引用的区别?
  2. 什么是移动语义?
  3. 如何实现移动语义?
  4. move和forward函数的作用

右值引用

右值:临时对象,无名,不能对它使用取地址符

常见类型:字面量、表达式、返回值的函数

右值引用:右值引用导致右值被存储到特定位置,且可以获取地址(引用C++ Primer Plus)

 与左值引用的区别?

 左值右值
意义有名对象临时对象
取地址可用取地址符&获取地址不可
常见类型 字面量、表达式、返回值的函数
声明引用&&&
用处 实现移动语义,减少内存复制

 移动语义

vector<string> method1(const vector<string>& V){
    vector<string> V1;
    //V1是对V处理后得到的
    return V1;
}
int main(){
    vector<string> V;
    //给V填充内容
    vector<string> V2 = method1(V);
}

编译器会把V1复制给临时返回对象,把临时返回对象复制给V2,再把临时返回对象销毁,移动语义直接把临时对象的数据访问权给V2,从而避免内存中数据复制

就像电脑中文件的移动其实只是修改了记录,文件还是在硬盘中的同一个地方

实现移动语义

  • 提供移动构造、赋值函数(转移数据),参数是右值,以区分复制构造、赋值函数
  • 通过传递右值(表达式)来调用
using namespace std;
class TestClass{

    TestClass(const TestClass &t){

    }
    TestClass(TestClass &&t){

    }
};
int main(){
    TestClass t1,t2;
    TestClass t3 = t1;//调用拷贝构造
    TestClass t4 = t1+t2;//调用移动构造
}

 move和forward

  • move:有时想对左值进行移动,可以用move将它强制转成右值,从而调用移动
  • forward:模板函数中,把模板参数传递给另一个调用函数时,实现完美转发(参数以及左右值类型一起转发),左值->左值、右值->右值
    • 函数模板的参数类型为 T&&
    • forward对传入的参数进行转发
    • //代码引自http://c.biancheng.net/view/7868.html
      //重载被调用函数,查看完美转发的效果
      void otherdef(int & t) {
          cout << "lvalue\n";
      }
      void otherdef(const int & t) {
          cout << "rvalue\n";
      }
      //实现完美转发的函数模板
      template <typename T>
      void function(T&& t) {
          otherdef(forward<T>(t));
      }

       

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值