IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 系统运维 -> 默认构造函数,拷贝构造函数,移动构造函数实例 -> 正文阅读

[系统运维]默认构造函数,拷贝构造函数,移动构造函数实例

直接上例子,更能清楚的显示区别:
(例子参考自c++ primer 5th 课后题)
例子1:

#include<iostream>
#include<vector>
using namespace std;
struct X {
    X() { std::cout << "X()" << std::endl; }
    X(const X&) { std::cout << "X(const X&)" << std::endl; }
    X& operator= (const X& x);
    ~ X() { std::cout << "~X()" << std::endl; }
};

X& X::operator=(const X& x)
{
	// 实际上这里没有输出
    std::cout << "=X()" << std::endl;
}

void f (X& x1, X* x2)
{
    vector<X> xvec;
    xvec.push_back(x1);
    xvec.push_back(*x2);
    cout << "------- destructor in f -----" << endl;
}

int main(){
	cout << "------- constructor -----" << endl;
    X x1;
    X *x2 = new X();
    cout << "------- copy constructor -----" << endl;
    f (x1, x2);
    // f()结束会调用一次析构
    cout << "------- destructor 1-----" << endl;
    delete x2;
    cout << "------- destructor 2-----" << endl;
	return 0;
}

运行结果:
这里有个STL的知识点,为什么会在------- copy constructor -----之后会再拷贝一次和析构一次,因为vector容器一开始给的capable_size是1,当你push_back第二的对象时,就要重新开辟空间(一般来说是按照两倍空间扩容为2),把原来的东西拷贝过去,然后析构原来的空间,所以这里多调用了一次拷贝和析构。对应的你要push_back第三个时就会再次扩容(再次两倍空间扩容为4),大家可以自己试试,这里就不再展示。

------- constructor -----
X()
X()
------- copy constructor -----
X(const X&)
X(const X&)
X(const X&)
~X()
------- destructor in f -----
~X()
~X()
------- destructor 1-----
~X()
------- destructor 2-----
~X()

例子2:

#include<iostream>
using namespace std;
// .h文件
class HasPtr {
    friend void swap(HasPtr&, HasPtr&);
public:
	HasPtr(const std::string &s = std::string()) : ps(new std::string(s)), i(0){}

	HasPtr(const HasPtr& hp) : ps (new std::string(*hp.ps)), i (hp.i) {}
	HasPtr& operator= (const HasPtr& hp)
	{
	    auto newp = new std::string(*hp.ps);
	    delete ps;
	    ps = newp;
	    i = hp.i;
        return *this;
	}

	std::string& getPs()
	{
	    return *ps;
    }

	~HasPtr () { delete ps; }
private:
    std::string *ps;
    int i;
};

inline void swap(HasPtr& lhs, HasPtr& rhs)
{
    using std::swap;
    swap (lhs.ps, rhs.ps);
    swap (lhs.i, rhs.i);
    std::cout << "call the swap function." << std::endl;
}

// 测试 .cpp
int main()
{
    HasPtr hp1 ("hello");
    HasPtr hp2 ("world");

    swap(hp1, hp2);
    cout << hp1.getPs() << endl;
    cout << hp2.getPs() << endl;

    return 0;
}

运行结果:

call the swap function.
world
hello

例子3:

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
// .h文件,注意要重写operator=、swap函数;新增operator<函数。
class HasPtr {
    friend void swap(HasPtr&, HasPtr&);
    friend bool operator< (HasPtr& lhs, HasPtr& rhs);
public:
	HasPtr(const std::string &s = std::string()) : ps(new std::string(s)), i(0){}
	HasPtr(const HasPtr& hp) : ps (new std::string(*hp.ps)), i (hp.i) {}

	HasPtr& operator= (HasPtr hp)
	{
	    this->swap(hp);
        std::cout << "call operator=(HasPtr &rhs)" << std::endl;
	    return *this;
	}

	void swap(HasPtr &rhs)
    {
        using std::swap;
        swap(ps, rhs.ps);
        swap(i, rhs.i);
//        std::cout << rhs.getPs();
        std::cout << "call swap(HasPtr &rhs)" << std::endl;
    }

	std::string& getPs()
	{
	    return *ps;
    }

	~HasPtr () { delete ps; }
private:
    std::string *ps;
    int i;
};

void swap(HasPtr& lhs, HasPtr& rhs)
{
    lhs.swap(rhs);
}

bool operator< (HasPtr& lhs, HasPtr& rhs)
{
	std::cout << lhs.getPs() <<" "<<rhs.getPs()<<" "<<(*lhs.ps < *rhs.ps)<<endl;;
    return *lhs.ps < *rhs.ps;
}

// .cpp文件
int main()
{
	HasPtr hp1 ("Anna");
    HasPtr hp2 ("hello");
    HasPtr hp3 ("world");
    vector<HasPtr> hvec;
    hvec.push_back(hp1);
    hvec.push_back(hp2);
    hvec.push_back(hp3);

    std::sort (hvec.begin(), hvec.end());

    for (auto i : hvec) {
        cout << i.getPs() << endl;
    }
    
    return 0;
}

运行结果:
具体底层是怎么实现的有知晓的小伙伴可以评论区补充一下。

hello Anna 0
hello Anna 0
call swap(HasPtr &rhs)
call operator=(HasPtr &rhs)
world Anna 0
world hello 0
call swap(HasPtr &rhs)
call operator=(HasPtr &rhs)
Anna
hello
world

例子4:

#include <iostream>

class HasPtr {
    friend void swap(HasPtr&, HasPtr&);
    friend bool operator< (HasPtr& lhs, HasPtr& rhs);
public:
	HasPtr(const std::string &s = std::string()) : ps(new std::string(s)), i(0){}

	HasPtr(const HasPtr& hp) : ps (new std::string(*hp.ps)), i (hp.i) {}

	HasPtr& operator= (HasPtr hp)
	{
	    this->swap(hp);
	    std::cout << "call operator=(HasPtr &rhs)" << std::endl;
	    return *this;
	}
    HasPtr (HasPtr&& hp) noexcept;
//    HasPtr& operator= (HasPtr&& hp) noexcept;

	void swap(HasPtr &rhs)
    {
        using std::swap;
        swap(ps, rhs.ps);
        swap(i, rhs.i);
        std::cout << "call swap(HasPtr &rhs)" << std::endl;
    }

	std::string& getPs()
	{
	    return *ps;
    }

	~HasPtr () { delete ps; }
private:
    std::string *ps;
    int i;
};

void swap(HasPtr& lhs, HasPtr& rhs)
{
    lhs.swap(rhs);
}

// HasPtr.cpp
using namespace std;
HasPtr::HasPtr(HasPtr&& hp) noexcept : ps (hp.ps), i (hp.i)
{
    hp.ps = nullptr;
    cout << "call move constructor." << endl;
}

int main()
{
    HasPtr hp1("hello"), hp2("world");
    //hp1 = hp2;
    hp1 = std::move (hp2);
    cout << hp1.getPs() << endl;
    return 0;
}

运行结果:

call move constructor.
call swap(HasPtr &rhs)
call operator=(HasPtr &rhs)
world

  系统运维 最新文章
配置小型公司网络WLAN基本业务(AC通过三层
如何在交付运维过程中建立风险底线意识,提
快速传输大文件,怎么通过网络传大文件给对
从游戏服务端角度分析移动同步(状态同步)
MySQL使用MyCat实现分库分表
如何用DWDM射频光纤技术实现200公里外的站点
国内顺畅下载k8s.gcr.io的镜像
自动化测试appium
ctfshow ssrf
Linux操作系统学习之实用指令(Centos7/8均
上一篇文章      下一篇文章      查看所有文章
加:2021-11-27 10:18:21  更:2021-11-27 10:20:26 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/16 1:45:46-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码