【发布时间】:2021-12-18 20:23:10
【问题描述】:
我对下面的代码有点困惑:
struct A {
std::atomic<int> a = 0;
};
这会报错:
复制“std::atomic”类型的成员子对象调用已删除的构造函数
但几乎相同的代码确实有效:
struct A {
std::atomic<int> a = {0};
};
好吧,如果第一个变体需要复制构造函数,那么它必须使用operator=()。可是等等!此运算符在没有复制构造函数的情况下完美工作:
A a;
a.a = 1;
谁能解释一下这两种就地初始化是如何在简单操作方面进行扩展的?为什么第一个需要复制构造函数?
【问题讨论】:
-
请记住,复制赋值不使用复制构造函数。
std::atomic<int> a = 0涉及复制构造函数。a.a = 1只是分配,甚至不是复制分配。不过我无法回答,因为我不知道为什么std::atomic<int> a = {0}会成功,我本来预计会失败。 -
@MooingDuck 我一直认为,
std::atomic<int> a = 0应该等于std::atomic<int> a(0)- 没有复制构造函数,但看起来不是。 -
std::atomic<int> a = 0将需要一个复制构造函数在语法上,因此 C++ 规范说此语法需要复制构造函数可用。但是,使用复制构造函数将是不必要的开销,因此 C++ 规范还说可以省略复制构造函数,这使其 表现 与std::atomic<int> a(0);相同。请注意,此行为仍需要复制构造函数理论上可用。 -
@MooingDuck 感谢您的解释,我不知道。您的评论包含一半的答案。
-
@MooingDuck 它并不严格要求复制构造函数,移动构造函数足以进行复制初始化。
标签: c++ c++11 initialization atomic copy-constructor