为什么需要使用复制构造函数来启用复制省略?

时间:2019-02-18 05:07:44

标签: copy copy-elision

我有以下代码使用-std=c++17编译器通过编译标志-std=c++2@C++2@(GNU)测试RVO

struct C
{
    C() = default;
    C(const C& obj){PrintAddress("copy ctor"); }

    void PrintAddress( std::string mark = "") const { std::cout << "> " << mark << "\t" << this << '\n'; }
};

C get() { C c; c.PrintAddress("get()"); return c; }

int main()
{
    C rvo = get();
    rvo.PrintAddress("rvo's");
}

它输出:

> get() 0x7ffe7467db7c
> rvo's 0x7ffe7467db7c

但是,如果使用默认的副本构造函数:

struct C
{
    C() = default;
    C(const C& obj) = default;

    void PrintAddress( std::string mark = "") const { std::cout << "> " << mark << "\t" << this << '\n'; }
};

输出变为:

> get() 0x7ffff37e7b4c
> rvo's 0x7ffff37e7bac //emmmm

复制省略已禁用。

基于reference,在以下情况下需要复制省略号:

  

在以下情况下,允许编译器,但即使复制/移动(自C ++ 11起)构造函数和析构函数也不需要省略类对象的复制和移动(自C ++ 11起)构造有明显的副作用。这些对象直接构造到存储中,否则会将它们复制/移动到其中。这是一种优化:即使发生并且未调用copy / move(由于C ++ 11)构造函数,它仍然必须存在并且可以访问(好像根本没有优化发生) ,否则程序格式不正确

所以,我的理解是没有复制构造函数,没有复制省略。我的问题是为什么呢?复制构造函数甚至不会在复制省略中调用。为什么必须提出?

0 个答案:

没有答案