什么是正确的实现移动构造函数(和其他)
What is the correct implementation of move constructor (and others)?
我有一个包含std::vector的简单类,我希望在按值返回类时受益于移动语义(不是RVO)。
我以以下方式实现了移动构造函数、复制构造函数和复制赋值操作符:
class A
{
public:
// MOVE-constructor.
A(A&& other) :
data(std::move(other.data))
{
}
// COPY-constructor.
A(const A& other) :
data(other.data)
{
}
// COPY-ASSIGNMENT operator.
A& operator= (const A& other);
{
if(this != &other)
{
data = other.data;
}
return *this;
}
private:
std::vector<int> data;
};
以上实现正确吗?
还有另一个问题:我是否需要实现这些成员,或者它们是由编译器自动生成的?我知道复制构造函数和复制赋值操作符是默认生成的,但是编译器也可以自动生成移动构造函数吗?(我用MSVC和GCC编译这段代码)
提前感谢任何建议。(我知道已经有一些类似的问题,但不是针对这个确切的场景。)
对于这个类[*]来说,它们都是不必要的,因为如果你没有声明它们,它就会有隐式的。
你的构造函数很好。下面的代码表面上调用move构造函数:
A f() { return A(); }
A a = f(); // move construct (not copy construct) from the return value of f
实际上可能会触发move-省略,在这种情况下,实际上只调用无参数的构造函数。我假设您计划提供一些构造函数,而不是复制和移动;-)
你的拷贝赋值很好,它与隐式赋值的区别只是在于它有自赋值检查,而隐式赋值没有。我认为我们不应该争论自赋值检查是否值得,这并不是不正确的。
没有定义移动赋值操作符。如果你定义了其他的,你应该这样做,但是如果你去掉了其余的,它就是隐式的[*]。move赋值操作符(无论是用户定义的还是隐式的)确保以下代码将移动而不是复制:
A a;
a = f();
[*]在一个已完成的c++ 11实现上,到目前为止还不存在。您可以在每个编译器的基础上检查此功能是否已经实现,并且可能在MSVC实现之前,您将以一些可怕的#define
恶作剧告终。
对于这个确切的场景,您不需要声明任何移动/复制/赋值函数。编译器会生成正确的默认值
相关文章:
- 如何在其他类中使用参数化构造函数制作类的对象?
- 通过向构造函数其他对象引用页面来创建对象
- 为什么构造函数的虚拟函数调用有时有效,但其他调用却无效
- 继承构造函数和其他变量的解决方法
- 其他结构中的结构构造函数
- C++编译错误是由于使用 std::move 时运动构造函数与其他非运动构造函数之间的冲突
- 在其他构造函数的调用中调用构造函数时C++编译错误
- C++ 在构造函数中传递数组而不在其他地方定义它们
- 为什么删除的复制构造函数不允许使用其他具有多态类型的构造函数?
- 可以移动构造函数以除班级本身以外的其他参数
- 使用构造函数的可变参数中的其他模板化类执行模板化类的初始化
- 构造函数期望缺少对其他构造函数的调用/候选人期望 1 个参数,提供 0?
- 作为其他类成员的类:创建一个接受所有数据的构造函数
- 在构造函数以外的任何其他位置访问相机时,我的相机指针返回 null
- 构造函数找不到合适的定义,以及 100 个其他错误?
- 委托构造函数和默认参数,具体取决于其他参数
- 构造函数调用其他构造函数
- C 实例化对象,在没有指针的情况下,其他类构造函数中没有默认构造函数
- 当存在其他构造函数时,如何强制创建默认序列构造函数
- 来自没有默认构造函数的超级类的子类,而无需调用任何其他构造函数