我有一个简单的代码:
# include <atomic>
int main()
{
std::atomic<int> a = 0;
}
这段代码在GCC11.1.0中使用-std=c17可以很好地编译,但在-std=c14和-std=c11中编译失败。
使用已删除的函数std::atomic::atomic(const std::atomic&)
为什么呢?在c17类中 std::atomic
仍然没有复制构造函数。为什么此代码对-std=c17有效?
当然,我知道首选的样式是使用 {}
,但我只是好奇为什么上面的代码自c17以来编译得很好。
1条答案
按热度按时间bmp9r5qi1#
由于c17,这样的拷贝省略是有保证的。对于
std::atomic<int> a = 0;
,a
需要从中初始化0
直接的。注意:上面的规则没有指定优化:PR值和临时的C 17核心语言规范与早期C修订的根本不同:不再有临时的复制/移动。描述c17机制的另一种方法是“非物质化的值传递”:返回和使用prvalues,而从不具体化临时值。
在c17之前,即使复制/移动操作(初始化
a
从临时std::atomic<int>
从哪个开始初始化0
)可能已优化(在复制初始化中),复制/移动构造函数仍然需要可访问。最后一步通常是优化出来的,转换的结果直接在为目标对象分配的内存中构造,但是即使没有使用,也需要相应的构造函数(move或copy)来访问(直到c17)