强制复制构造函数

时间:2014-03-10 13:11:22

标签: c++11 move-semantics

我有这样的功能:

Object Class::function() {
    Object o;
    return o;
}

现在当我这样称呼它时:

Object o = Class::function();

它想要使用移动构造函数。但是我希望它使用复制构造函数。如何强制它不使用移动构造函数?我删除了移动构造函数但后来无法编译。

编辑:我的构造函数看起来像这样:

Object(const Object & other) { ... }
Object(Object & other) { ... }
Object(Object && other)=delete;

1 个答案:

答案 0 :(得分:4)

如果您有一个用户声明的(手动声明的)copy ctor,则不会隐式声明move ctor。只是忽略移动ctor,它不会参与重载解析(即不要将其定义为已删除,只是省略整个声明)。

CWG DR 1402之后,解释略有不同:即使存在用户声明的复制ctor,也会始终声明移动ctor,但它将被隐式定义为已删除。并且有一个特殊情况,这个删除使得移动不参与重载解析。注意:如果您明确删除了移动ctor,那仍然意味着“如果通过重载解析选择了此功能,则程序格式错误”。特殊情况适用于移动ctor默认(显式或隐式),并且当这导致移动ctor被定义为已删除时(作为为默认函数提供的隐式定义)。

#include <iostream>

struct loud
{
    loud() { std::cout << "default ctor\n"; }
    loud(loud const&) { std::cout << "copy ctor\n"; }
    loud(loud&&) { std::cout << "move ctor\n"; }
    ~loud() { std::cout << "dtor\n"; }
};

struct foo
{
    loud l;
    foo() = default;
    foo(foo const& p) : l(p.l) { /*..*/ }; // or `= default;`
    // don't add a move ctor, not even deleted!
};

foo make_foo()
{
    return {{}};
}

int main()
{
    auto x = make_foo();
}

注意复制省略(例如使用-fno-elide-constructors)。输出:

default ctor
copy ctor
dtor
dtor

Live example