假设我有一个包含向量的简单结构并定义了一个复制赋值运算符,以及一个返回此结构的函数,如下所示:
struct SimpleStruct
{
vector< int > vec1;
operator=( SimpleStruct& other )
{
vec1 = other.vec1;
}
}
SimpleStruct GetStruct();
据我了解,因为我已经声明了一个复制赋值运算符,编译器不会自动为SimpleStruct生成一个移动构造函数。
所以如果我像这样使用GetStruct
函数:
SimpleStruct value = GetStruct();
当我说vec1 = other.vec1;
时,编译器是否足够智能移动而不是复制向量?或者我是否需要为SimpleStruct明确定义移动构造函数/赋值运算符以利用向量移动?
答案 0 :(得分:3)
C ++ 11对允许移动的时间有非常严格的规定。除非涉及临时性,否则这些规则要求明确使用std::move
或类似的强制转换(例如std::forward
)。
是的,你可以移动一些东西。但这不会偶然发生;它必须是故意的。
此外,编写一个可以修改复制内容的复制赋值运算符通常很粗鲁。这就是为什么他们通常采用const&
,这几乎可以保证无法移动。
或者我是否需要为SimpleStruct显式定义移动构造函数/赋值运算符以利用向量移动?
通常,这就是不明确定义复制和移动构造函数的原因。让编译器完成它的工作并为你生成(除非你使用VC ++,它不会为移动构造函数/赋值做它的工作)。只显示为较低级别容器写入复制/移动构造函数;任何更大的东西都应该依靠这些价值类型来完成他们的工作。
答案 1 :(得分:1)
在复制构造函数或复制赋值运算符中,复制意味着复制。语言永远不会根据函数的调用方式对函数内容进行任何上下文调整。
但是,SimpleStruct value = GetStruct();
可能不会发生副本,因为copy elision适用。