【发布时间】:2016-07-25 01:37:16
【问题描述】:
我有以下非常简单的类:
class Foo
{
public:
Foo() {}
Foo(const Foo&) = delete;
Foo(Foo&&) {}
void operator=(const Foo&) = delete;
void operator=(Foo&&) {}
void dump() const {}
};
该类是可移动构造和可分配的,但不是可复制构造和可分配的。
我想使用向量的初始化列表来初始化 Foo 元素的向量。
std::vector<Foo> vf = { Foo() };
编译器抱怨,因为代码必须使用已删除的复制构造函数。谁能解释一下,为什么在这种情况下不使用 move 构造,以及为什么需要对象的副本?
以下也需要复制构造函数,也不起作用:
std::vector<Foo> vf = { std::move(Foo()) };
另一方面,这很好用(调用了移动构造函数):
std::vector<Foo> vf;
vf.push_back(Foo());
感谢您的解释... :)
更新:
建议的this 帖子解释了我的问题。
此外,让我们考虑以下代码(连同上面的class Foo):
class Bar {
public:
Bar(std::initializer_list<Foo> _l) {
std::cout << "Bar::Bar()" << std::endl;
for (auto& e : _l)
e.dump();
}
};
int main() {
Bar b { Foo() };
return 0;
}
这会产生以下输出(使用 C++11 编译):
Foo::Foo()
Bar::Bar()
Foo::dump()
Foo::~Foo()
可以看出,初始化列表实际上并没有用大括号之间的“对象副本”填充。从 C++14 开始,这可能不是真的。
【问题讨论】:
-
这里有你需要的所有解释:stackoverflow.com/questions/8193102/…
-
是的,它解释了。谢谢。
标签: c++ move-semantics initializer-list