5

当我阅读有关移动语义和右值引用的示例时,它们正在利用右值引用的优势并围绕包装指针的大对象移动语义, 例如 1 2

例如,他们只是复制移动对象内部的指针并将其设置为nullptr. (移动/交换)

我的问题是,对于没有指针但它们很大的对象,移动语义是否有任何优势(性能)?

class BigClass
{
   int data[BIG_SIZE];
   int a01;
   .
   .
   . many members
   .
   .
   int z99;

public:

   move constructor ?!
};
4

3 回答 3

10

对于没有指针但它们很大的对象,移动语义是否有任何优势?

它在性能方面没有任何优势,因为正如您所注意到的,您将无法快速“窃取”被移动对象的内脏。

但是,从纯逻辑的角度来看,您的类的语义可能是您的对象不应该是可复制的,因此不能/不应该提供复制构造函数。

例如, a 的内部unique_ptr不是任何可以移动得比复制快的东西(它是原始指针上的零开销包装器),但是语义约束使得复制 a 成为不可能unique_ptr。在这种情况下,移动语义就是保持程序中某个时间点必须存在一个 unique_ptr指向某个对象的不变性。

因此,移动构造函数(或移动赋值运算符)unique_ptr也必须重置被移动的指针以保持不变量。

您的类可能与 a 完全不同unique_ptr,并且可能相当重,但可能仍然存在使其不可复制的语义约束。在这种情况下,可以利用移动语义来强制执行正确的不变量。

于 2013-05-24T14:06:38.683 回答
1

正如您所指出的,由于每个对象都保留其所有数据的副本并且没有要传输的指针,因此不可能进行浅拷贝。根据情况,将另一个对象设置回其默认状态可能是有意义的,但这是移动构造函数和复制构造函数之间唯一可能的区别。

于 2013-05-24T13:59:09.747 回答
0

在 SO 中随机冲浪,我发现 move semantics proposal。有一段话是我的回答:

对于 POD,移动和复制是相同的操作(一直到机器指令级别)。

于 2016-07-15T05:09:18.597 回答