【问题标题】:Moving an object that contains values移动包含值的对象
【发布时间】:2021-04-18 05:28:04
【问题描述】:

我有这样的课:

class Bla {
private:
    size_t length;
    ComplexClass expensiveData; // Very expensive, and Bla manages everything about someStuff, including its creation and deletion
};

现在假设我想做这样的事情:

Bla a = ...;
Bla b = ...;

a = b;

现在我认为会发生的是,当我将a 分配给b 时,将调用复制分配运算符。

问题是,如果我要深度复制ab 的内容,那将是非常昂贵的。最好总是只做一个Bla 的浅拷贝。然而,问题在于expensiveData 是一个常规值,而不是一个指针,这意味着如果我尝试将expensiveData 重新分配给一个新对象,它只会复制它。

另外,expensiveData 由我使用的其中一个库提供,我无法更改它的工作方式。

我应该要么:

  1. 删除复制赋值和复制构造操作符,因为我从不想做任何深拷贝,但随后就失去了赋值的能力。
  2. expensiveData更改为指针,然后在复制构造函数中重新分配指针。
  3. 使用其他方法,例如std::movestd::swap

【问题讨论】:

  • expensiveData 的实际确切类型是什么?是什么让复制变得昂贵? (edit您的问题包括此信息,而不是在评论中回复。)
  • expensiveData 是我从我提供的一个库中使用的某种树形结构(我无法更改它的工作方式)。

标签: c++ memory-management


【解决方案1】:

存储指向ComplexClass 的指针会起作用,但使用 raw 指针是不明智的。使用std::shared_ptr<ComplexClass>

或者,您可以删除复制构造函数和赋值,然后在需要赋值时将 Bla 存储在 shared_ptrs 中。

除了删除复制操作之外,您还可以:

  • 将它们设为私有,并添加一个具有可怕名称的成员函数来执行它们,以备不时之需。
  • 仅删除复制分配,并创建复制构造函数explicit。然后a = b; 不会编译,但a = Bla(b); 仍然可以。

【讨论】:

  • 嗯,好的。我想我将使用最后一个选项,即删除复制赋值运算符但保留复制构造函数,因此我仍然可以轻松复制它。谢谢!
猜你喜欢
  • 1970-01-01
  • 2013-05-30
  • 1970-01-01
  • 2013-01-10
  • 2017-08-29
  • 2021-09-07
  • 1970-01-01
  • 2012-03-12
相关资源
最近更新 更多