0

我在理解 C++ 复制构造函数时遇到了一些问题,希望有人能帮助我。

据我所知,当函数返回类的实例时(除其他外)会调用复制构造函数。

#include <iostream>
using namespace std;

class Test
{
    int a;
public:
    Test(int a) : a(42) 
    {}

    // Copy constructor
    Test(const Test& other) 
    {
        cout << "copy constructor" << endl;
    }
};

Test test_function()
{
    Test a(3);
    return a;
}

int main()
{
    test_function();
    return 0;
}

那么,如果我执行这段代码,复制构造函数永远不会被调用?为什么?然后返回哪个对象?

此外,如果我更换线路

test_function();

Test b = test_function();

复制构造函数都没有被调用——为什么不呢?

提前致谢

编辑:将功能更改为:

Test test_function()
{
    Test a(3);
    Test b(34);

    if (4 < 2)
        return a;

    else
        return b;
}

可以看到复制构造函数调用,因为编译器无法使用 RVO。

4

2 回答 2

0
Test test_function()
{
    Test a(3);
    return a;
}

此函数声明Test并返回它的本地副本。编译器将看到这一点,并意识到它将在创建新副本时销毁本地副本,并简单地将本地副本省略到结果中。要查看您想要的结果,这可能会更好:

Test test_function(const Test& t)
{
    return t;
}

int main()
{
    Test t1;
    Test t2 = test_function(t1);
    return 0;
}
于 2013-10-25T21:31:50.267 回答
0

它是(复制/移动)构造函数省略作为一种优化,以避免不必要的复制/移动。可以应用的另一个优化是完全忽略返回任何内容,因为您根本没有使用返回的值。

无论如何,您可以禁用此优化并通过此编译器开关(gcc)查看您想要的消息:

-fno-elide-constructors

但是,仅将上述开关用于测试,并让优化应用于实际程序。

于 2013-10-25T21:40:01.730 回答