c++ - 调用复制构造函数时如何复制内存?

标签 c++ compiler-optimization copy-constructor

我试图了解复制构造函数的行为以及如何创建和复制内存和临时对象。我在 g++ 中禁用了复制省略,以便更好地了解正在发生的情况。这是我的代码:

//====================
#include <iostream>
using namespace std;

class Human
{
public:
    Human()
    {
        cout << "Human constructed: " << this << endl;
    }

    Human(const Human &)
    {
        cout << "Human copied:      " << this << endl;
    }

    ~Human()
    {
        cout << "Human destroyed:   " << this <<  endl;
    }
};

class Creature
{
public:
    Creature()
    {
        cout << "Creature constructed: " << this <<  endl;
    }

    ~Creature()
    {
        cout << "Creature destroyed:   " << this <<  endl;
    }

    Human create_human()
    {
        Human mySecondHumanObject;
        return mySecondHumanObject;
    }
};


int main()
{
    Creature myCreatureObject;
    Human myFirstHumanObject = myCreatureObject.create_human();
    cout << "myFirstHumanObject :" << &myFirstHumanObject << endl;
    return 0;
}

输出:

Creature constructed: 0x7fff5b8d9d95
Human constructed: 0x7fff5b8d9d67    // mySecondHumanObject constructed
Human copied:      0x7fff5b8d9d97    // copied to where???
Human destroyed:   0x7fff5b8d9d67    // mySecondHumanObject destroyed at return
Human copied:      0x7fff5b8d9d96    // copied to myFirstHumanObject
Human destroyed:   0x7fff5b8d9d97    // object copied at return now destroyed
myFirstHumanObject :0x7fff5b8d9d96
Human destroyed:   0x7fff5b8d9d96
Creature destroyed:   0x7fff5b8d9d95

有人可以解释一下这个机制是如何工作的吗?我有点困惑为什么第一次调用复制构造函数(复制到内存地址:0x7fff5b8d9d97)。为什么不直接复制到 myFirstHumanObject 的内存地址:0x7fff5b8d9d96)?

最佳答案

如果您要编写简单的 myCreatureObject.create_ human(); 而不将结果分配到任何地方,那么 Human 不会被创建和销毁吗?当然它会存在,并且您会看到输出。该函数返回一个值,因此必须使用该值创建一个临时对象。

由于您关闭了复制省略,因此需要创建该临时对象,即使在使用它来初始化另一个对象时也是如此。复制省略通常消除的不仅仅是一份拷贝。它可以消除整个链条。当它关闭时,这些链条会重新出现,就像你看到的那样。

关于c++ - 调用复制构造函数时如何复制内存?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53099960/

相关文章:

c++ - 在 ASIO 中对 UDP 调用 receive_from 应用超时

llvm - LLVM 做了哪些类型的优化以及它的前端必须自行实现哪些类型的优化?

c++ - 在什么情况下我必须为我的 C++ 类提供赋值运算符、复制构造函数和析构函数?

java - 什么是好的做法?复制构造函数或防御复制方法

具有多个原始指针的 C++ 构造函数

c++ - 无限循环 vs boost::asio::deadline_timer C++ 性能

c++ - C++ 构造函数错误

c - 为什么 GCC 会为几乎相同的 C 代码生成如此截然不同的程序集?

c++ - 图像部分的Opencv高度/宽度

c++ - 关于优化不会出现在 EXE 中的 DLL 有什么注意事项吗?