为什么复制构造函数被称为两次

时间:2015-09-05 06:35:54

标签: c++

对于以下代码,复制构造函数调用两次为什么?

#include <iostream>
using namespace std;
class A {
    int X;
public:
    A() {
        cout << "Simple Constructor" << endl;
    }
    A(int b) :X(b) {
        cout << "Constructor " << X << endl;
    }
    A(const A& obj) :X(obj.X) {
        cout << "Copy Constructor " << endl;
    }
    ~A() {
        cout << "Destructor " << X << endl;
    }
};
A fun(A obj) {
    cout << "Fun" << endl;
    return obj;
}
int main() {
    A obj(10);
    obj = fun(obj); // here is confusion
    cout << "End" << endl;
    return 0;
}

输出:

Constructor 10
Copy Constructor
Fun
Copy Constructor
Destructor 10
Destructor 10
End
Destructor 10

由于临时对象,我期待可能是第二个复制构造函数。你说什么?

1 个答案:

答案 0 :(得分:1)

当您调用fun(obj)时,将执行复制构造函数的第一次调用。您通过值传递obj,因此将其复制并在函数内部使用该副本。 当您有趣地返回obj时,将执行下一个副本。它也是按值返回的,因此会再次复制。

我不知道你的意图是什么。如果你想在函数中修改对象,最好通过引用传递它并使函数为void:

void fun(A& obj) {
    cout << "Fun" << endl;
}

然后致电

fun(obj);

这样就可以防止两次调用复制构造函数。

编辑:

如果您想知道为什么不执行返回值优化,您应该知道它是可选行为,标准允许编译器。首先,您应该确保允许编译器优化代码(例如,您不使用Debug Build),然后它实际上支持RVO。最后你应该考虑在这种情况下优化是否真的有意义。您的对象内部只有一个int,因此它具有基本类型的大小。 关于优化的一件事要记住它可以执行,但编译器决定是否执行它。