c++11的右值引用相关

c++11新的移动语义确实可以减少了不必要的对象拷贝工作,但是由此引发的左值右值语法却着实令人讨厌,尤其是在模板推导时的引用折叠操作真的是服气,关于引用折叠及完美转发《深入理解c++11》和《深入应用c++11》这两本书都有做介绍。

看了几篇大佬博客,有所收获却头皮发麻,记录如下:

1.https://blog.csdn.net/linuxheik/article/details/69536909?utm_medium=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-2.control&depth_1-utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-2.control

2.https://blog.csdn.net/WizardtoH/article/details/80718605?utm_medium=distribute.pc_relevant_t0.none-task-blog-BlogCommendFromMachineLearnPai2-1.control&depth_1-utm_source=distribute.pc_relevant_t0.none-task-blog-BlogCommendFromMachineLearnPai2-1.control

3.https://blog.csdn.net/guangcheng0312q/article/details/103572987?utm_medium=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-1.control&depth_1-utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-1.control

4.https://www.douzhq.cn/c11_5/

总结:

1.c++11后类中多了两种构造函数(移动构造A(A&& tmp)和移动赋值operator(A&& tmp) ),临时类A不能是const的,因为要将其里边所带的指针移动到this后置空,这个没啥好说就是提升了效率,减少临时对象的构造和析构消耗

其伪码如下

1
2
3
4
5
6
A(A&& tmp):ptr(tmp.ptr)//初始化列表里将A类的成员ptr进行复制操作,使this->ptr和tmp.ptr指向一样,相当于浅拷贝
{
 
  tmp.ptr=nullptr; //置空,不然就和浅拷贝一样两个指针指向同一块内存,两个指针析构两次必出问题
 
}

2.在函数模板中做类型传递的时候,由于模板类型推导而形成的诡异操作

例如下边的函数模板,f的参数T&&,第一眼我们肯定觉得他是右值引用,但是其实不然,T&&当传入的实参是左者引用是会被折叠为T&,当为右值引用时才是我们理解的T&&,

tempalte<typename Tvoid f(T&&);

《effective modern c++》第一讲就是关于模板类型推导

3.引用折叠

其实就是模板参数传入的是左值引用还是右值引用的使其产生不同的推导参数,与上一点讲的是同一件事。

4.完全转发

下边这个大佬写了个小例子可以说明完全转发的作用

https://www.douzhq.cn/c11_5/

示例代码如下:

复制代码
#include <iostream>
#include <stdlib.h>
#include <type_traits>

void func(int& t)
{
    std::cout << "func(int& t)" << std::endl;
}

void func(const int& t)
{
    std::cout << "func(const int& t)" << std::endl;
}

void func(const int&& t)
{
    std::cout << "func(const int&& t)" << std::endl;
}

template<typename T>
void perfectForward(T&& t)
{
    func(std::forward<T>(t)); //完全转发
    //func(t); 
}

int main(int argc, char** argv)
{
    int a = 0;
    perfectForward(a);

    const int b = 20;
    perfectForward(b);

    perfectForward(std::move(a));

    system("pause");
    return 0;
}
复制代码

输出结果:

 

ps:关于右值在新标准中的具体使用大概只能从标准库里看看实现了,写了这么多还是云里雾里,只希望大伙不要被我误导哈哈,有时间去找找,单看这些概念并没有什么大用处。 

 

posted @   乐swap火  阅读(65)  评论(0编辑  收藏  举报
编辑推荐:
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
阅读排行:
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通
点击右上角即可分享
微信分享提示