iis服务器助手广告
返回顶部
首页 > 资讯 > 后端开发 > 其他教程 >C++移动语义介绍与使用讲解
  • 797
分享到

C++移动语义介绍与使用讲解

2024-04-02 19:04:59 797人浏览 安东尼
摘要

目录引入移动语义std::move引入移动语义 为了能够理解移动语义的目的,我们先从整成的一个类进行示范,示例如下: class TestClass { public: Te

引入移动语义

为了能够理解移动语义的目的,我们先从整成的一个类进行示范,示例如下:

class TestClass
{
public:
    TestClass(int s) :m_number(s) {
        cout << "constructor!\n";
    }
    ~TestClass() {
        cout << "destructor!\n";
    }
    // 拷贝构造
    TestClass(const TestClass& that) :m_number(that.m_number) {
        cout << "copy constructor!\n";
    }
    // 赋值操作符
    TestClass& operator=(const TestClass& tc) {
        cout << "operator= is called\n";
        if (this == &tc)
            return *this;
        m_number = 0;
        m_number = tc.m_number;
        return *this;
    }
    int m_number;
};
TestClass tcFactory()
{
    TestClass tc(10);
    return tc;
}
int main()
{
    {
        TestClass tc = tcFactory();
    }
    return 0;
}

上面代码的输出结果如下:

constructor!
copy constructor!
destructor!
destructor!

可以看到进行了一次构造和一次拷贝构造,拷贝构造就发生在tc 接收tcFactory()返回值时。这几产生了不必要的资源消耗,如果这里可以重用或者转移return产生的临时值(右值)是不是可以减少资源的消耗呢?c++正是使用转移的方式来处理的,这个转移就是移动构造函数,也可以说是移动语义,示例如下:

// 其他代码不变,只增加移动构造与移动赋值处理函数
// 移动构造
TestClass(TestClass&& rr):m_number(rr.m_number) {
    // 如果这里是指针的变量的话则可以避免指针重复释放的问题
    rr.m_number = 0;
    cout << "move constructor!\n";
}
// 移动赋值
TestClass& operator=(TestClass&& rr) {
    cout << "move operator= is called\n";
    if (this == &rr)
        return *this;
    // 此步骤相当于对源指针的释放
    m_number = 0;
    m_number = rr.m_number;
    return *this;
}

添加上述代码后,输出结果如下:

constructor!
move constructor!
destructor!
destructor!

此时第二次调用的就是移动构造,这样可以直接使用右值,避免重新申请空间,调用两次析构是因为,临时对象是被延长了声明周期,但最终也是要释放的。

std::move

前面看到移动构造接收的是右值引用,那么在需要对左值进行移动语义的时候(进行移动语义后,此左值以后将失效),那么就必须将左值转换为右值。此时td::move就很好的完成了这件事情,示例如下:

int main()
{
    vector<int> v{ 1,2,3,4 };
    // 拷贝构造
    vector<int> v1 = v;
    // 移动构造
    vector<int> v2 = std::move(v);
    cout << "v size():" << v.size() << "\n";
    cout << "v2 size():" << v2.size() << "\n";
    return 0;
}

上面输出代码为:

v size():0
v2 size():4

关于std::move注意的几点:

std::move本质上只是将传入的参数转换为一个右值,使用static_cast进行转换

std::move在进行类型推导时会保留形参的const属性,此时会造成一种使用失效的场景如下:

class TestClass
{
public:
	// 这么写在 VS中也会提示 	C26478 不要对常量变量使用 std::move
    TestClass(const string& str) :m_str(std::move(str)) {
    }
    string m_str;
};
int main()
{
    string str = "sss";
    TestClass tc(str);
    cout << tc.m_str << "\n";
    // 此处应该输出空,但实际并非如此 , 两个输出都是 sss
    cout << str << "\n";
    return 0;
}

到此这篇关于C++移动语义介绍与使用讲解的文章就介绍到这了,更多相关C++移动语义内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

--结束END--

本文标题: C++移动语义介绍与使用讲解

本文链接: https://www.lsjlt.com/news/166530.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • C++移动语义介绍与使用讲解
    目录引入移动语义std::move引入移动语义 为了能够理解移动语义的目的,我们先从整成的一个类进行示范,示例如下: class TestClass { public: Te...
    99+
    2024-04-02
  • C++移动语义详细介绍使用
    目录1.移动构造函数2.右值引用3.std::move()将左值强制转换为右值引用4.拷贝语义和移动语义1.移动构造函数 移动语义就是使用移动构造函数来构造对象。 我们知道在类中如果...
    99+
    2023-01-28
    C++移动语义 C++移动语义用法
  • C++movesemantic移动语义介绍
    目录前言移动构造为什么我们需要move semantic前言 在说移动语义之前 本文作者假设你已经具备了深拷贝浅拷贝左值右值等基本概念 本文不会再过多叙述 那么接下来 让我们开始吧 ...
    99+
    2024-04-02
  • C++的移动语义怎么使用
    这篇文章主要介绍“C++的移动语义怎么使用”的相关知识,小编通过实际案例向大家展示操作过程,操作方法简单快捷,实用性强,希望这篇“C++的移动语义怎么使用”文章能帮助大家解决问题。什么是移动语义移动语义是 C++11 中新增的一个语言特性,...
    99+
    2023-07-06
  • Python模块介绍与使用详细讲解
    目录模块的相关概念 1. 什么是模块2. 使用模块的好处模块的使用1. 自定义模块a) 方法一: 导入模块:b) 方法二c) 导入自己的模块Python中的包 1...
    99+
    2024-04-02
  • C/C++指针介绍与使用详解
    目录什么是指针定义指针变量间接引用指针常or常常指向指针的指针指针与数组指针的运算堆内存分配C语言C++语言指针与函数数组名作为函数的入口参数函数名作为参数传入其他函数使用指针修改函...
    99+
    2024-04-02
  • 一问了解C++的移动语义
    目录什么是移动语义?移动语义的好处通过右值使用移动语义移动语义的实例结论在 C++11 中,移动语义是一个重要的新特性,它可以使程序在内存管理方面更加高效,同时也提高了程序的性能。但...
    99+
    2023-05-15
    C++ 移动语义
  • C++BoostArray与Unordered使用介绍
    目录一、提要二、示例boost::array三、Boost.Unordered一、提要 Boost.Array 库在 boost/array.hpp 中定义了类模板 boost::a...
    99+
    2022-11-13
    C++ Array与Unordered C++ Boost Array C++ Boost Unordered
  • C语言深入讲解宏的定义与使用方法
    目录一、C语言中的宏定义二、宏定义表达式三、宏表达式与函数的对比四、有趣的问题五、强大的内置宏六、小结一、C语言中的宏定义 #define是预处理器处理的单元实体之一#define ...
    99+
    2024-04-02
  • C++学习之移动语义与智能指针详解
    目录移动语义 1.几个基本概念的理解 2.移动构造函数 3.移动赋值函数 4.std::move函数 5.面试题,关于实现String 资源管理和智能指针 一、C语言中的问题 二、C...
    99+
    2024-04-02
  • C语言中.与->的用法介绍
    目录(一)基础(二)例子(三)总结(一)基础 结构体用点,结构体指针用箭头。 a->b 的含义是 (*a).b 。  现代的标...
    99+
    2023-05-20
    C语言中.与->的区别 C语言->用法
  • 一文带你了解C++中的右值引用与移动语义
    目录意义左值右值值类别左值纯右值将亡值左值引用右值引用std::move()移动构造&移动赋值运算符重载测试&验证意义 充分利用临时对象,避免拷贝。 左值右值 值类别...
    99+
    2023-05-13
    C++右值引用 移动语义 C++右值引用 C++ 移动语义
  • C++左值与右值,右值引用,移动语义与完美转发详解
    目录C++——左值与右值、右值引用、移动语义与完美转发一、左值和右值的定义二、如何判断一个表达式是左值还是右值(大多数场景)三、C++右值引用四、std::m...
    99+
    2024-04-02
  • C语言中static的使用介绍
    目录1.static 可以修饰局部变量2. static 可以修饰全局变量3.static 可以修饰函数总结1.static 可以修饰局部变量 首先让我看看这段代码 #inclu...
    99+
    2024-04-02
  • Java注解的介绍和使用详细讲解
    文章目录 注解注解基本介绍自定义注解元注解注解解析 注解 注解基本介绍 注解概述: Java 注解(Annotation)又称 Java 标注,是 JDK5.0 引入的一种注释机制。 Java 语言中的类、构造器、方法...
    99+
    2023-08-16
    java junit 开发语言
  • C++右值引用,移动语义与完美转发得方法
    本篇内容主要讲解“C++右值引用,移动语义与完美转发得方法”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“C++右值引用,移动语义与完美转发得方法”吧!C++&mdash;&mda...
    99+
    2023-06-29
  • C语言举例讲解转义字符的使用
    目录前言啥是转义字符转义字符汇总表详解常见的转义字符总结前言 与大家一起理理转义字符。 啥是转义字符 简单理解:就是可以转换字符意思的字符。 转义字符汇总表 详解常见的转义字符 1...
    99+
    2024-04-02
  • C++中右值引用与移动语义的方法是什么
    今天小编给大家分享一下C++中右值引用与移动语义的方法是什么的相关知识点,内容详细,逻辑清晰,相信大部分人都还太了解这方面的知识,所以分享这篇文章给大家参考一下,希望大家阅读完这篇文章后有所收获,下面我们一起来了解一下吧。意义充分利用临时对...
    99+
    2023-07-05
  • React Fragment介绍与使用详解
    目录前言 Fragments出现动机 React Fragment介绍与使用 <React.Fragment> 与 <>区别 前言 在向 DOM 树批量添加...
    99+
    2024-04-02
  • C语言make和Makefile介绍及使用
    1:make和Makefile的介绍: 概念 在软件的工程中的源文件是不计其数的,其按照类型,功能,模块分别放在若干个目录中,哪些文件需要编译,那些文件需要后编译,那些文件需要重新编...
    99+
    2024-04-02
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作