【发布时间】:2013-06-01 12:37:10
【问题描述】:
为什么在此示例中没有打印任何内容?我在 Coliru 上用 Clang 编译。
#include <iostream>
struct S
{
S() noexcept = default;
S(S&&) noexcept { std::cout << "move-ctor"; }
};
void f(S) {}
int main()
{
f(S{});
}
【问题讨论】:
为什么在此示例中没有打印任何内容?我在 Coliru 上用 Clang 编译。
#include <iostream>
struct S
{
S() noexcept = default;
S(S&&) noexcept { std::cout << "move-ctor"; }
};
void f(S) {}
int main()
{
f(S{});
}
【问题讨论】:
编译器正在执行复制省略,即使您的移动构造函数、复制构造函数或析构函数有副作用,这也是 C++11 标准第 12.8/31 段所允许的:
当满足某些条件时,允许实现省略类的复制/移动构造 对象,即使为复制/移动操作选择了构造函数和/或对象的析构函数 有副作用。
复制省略这个术语即使在移动被省略时也被使用:
这种复制/移动操作的省略,称为复制省略,在以下情况下是允许的(其中 可以合并以消除多个副本):
[...]
——当一个尚未绑定到引用 (12.2) 的临时类对象将被复制/移动时 对于具有相同 cv-unqualified 类型的类对象,可以通过以下方式省略复制/移动操作 将临时对象直接构造到省略的复制/移动的目标中
[...]
使用 GCC,您可以使用 -fno-elide-constructors 来禁止复制省略。在这种情况下,您会看到调用了移动构造函数,如 live example。
【讨论】: