在被破坏的对象上移动构造函数?

时间:2017-04-14 14:35:59

标签: c++ move-semantics

我有一段代码

#include <iostream>

class A {
public:
    A() {
        std::cout << "Default constructor" << std::endl;
    }
    A(const A & other)
    {
        std::cout << "Copy constructor" << std::endl;
    }
    A(A && other)
    {
        std::cout << "Move constructor" << std::endl;
    }
    ~A()
    {
        std::cout << "Destructor" << std::endl;
    }
private:
    int i;
};

A && f()
{
    return A();
}

int main() {
    A a = f();
}

我尝试运行它,输出结果是

Default constructor
Destructor
Move constructor 
Destructor

我的问题是为什么在移动的构造函数之前调用析构函数?这是否也意味着第二个对象是用破坏的值构建的?

2 个答案:

答案 0 :(得分:6)

A && f()返回本地变量与A & f()具有相同的问题。它们都是参考文献。当您在a中构造main()时,本地变量已被销毁。这会导致对被破坏的实例的引用,从而导致未定义的行为。

如果您想在A()中将f()a移至main,只需按值返回即可。请尝试使用以下内容:

A f() {
    return A();
}

答案 1 :(得分:0)

第一个A对象是在f的调用堆栈框架中创建的。因此,当f将控制权返回给main时,必须销毁在f内创建的所有堆栈对象。这就是第一个析构函数被调用的原因。