c++ - 在什么情况下 operator= 应该用左值/右值重载而不是 copy-and-swap 来实现?

标签 c++ c++11 rvalue-reference

作为https://stackoverflow.com/a/3279550/943619巧妙地描述,实现 operator= 的正确方法通常是:

my_type& operator=(my_type other) {
    swap(*this, other);
    return *this;
}
friend void swap(my_type& lhs, my_type& rhs) { ... }  // This can vary some.

但是,Howard Hinnant 指出,有时您可以通过为左值和右值参数实现单独的重载来做得更好:

my_type& operator=(const my_type& other) { ... }
my_type& operator=(my_type&& other) { ... }

很明显,2 重载解决方案可以在多种情况下节省一步,但如此小的改进不太可能出现在基准测试中。相反,我正在寻找编写 2 个重载可以将性能提高一倍的情况。

最佳答案

“ copy-and-swap ”习惯用法的主要问题是效率较低。

即使我们有一个很好的 swap 实现,我们仍然同时拥有该类的 3 个实例,而左值和右值运算符的其他解决方案只有 2 个实例。

这意味着我们需要多 50% 的内存来进行 copy-and-swap ,而且它还可能需要大量的时间成本 - 因为您必须获取本来不需要的资源。

想想 std::vector 的情况:如果你做 vec1=vec2; 并且两者具有相同的大小,则使用左值引用 - 你不需要执行任何 newdelete 操作。在 copy-and-swap 中你必须创建第三个 vector - 所以你有一个额外的 newdelete 这可能会花费很多时间(如果 vector 很小它很重要)或大量内存(如果 vector 很大)

copy-and-swap 的主要优点是异常安全。 copy-and-swap 为您提供强大的异常安全性,但以性能为代价。

如果你需要异常安全——使用它。如果您需要性能(内存、时间、您的类获取的任何其他资源),请不要使用它。

关于c++ - 在什么情况下 operator= 应该用左值/右值重载而不是 copy-and-swap 来实现?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19523567/

相关文章:

c++ - string.empty() 或 string.size() == 0 哪个更快?

c++ - 为什么 Visual Studio 在这种情况下不执行返回值优化 (RVO)

c++ - 通过右值数据成员延长临时的生命周期适用于聚合,但不适用于构造函数,为什么?

c++ - 临时对象是 xvalues 吗?

c++ - 发送 native 消息而不运行新进程

c++ - 如何描述在 C++ 中使用全局变量的所有情况?

c++ - g++ 不包括它所说的为 C++11 包含的文件?

C++ 非 const 右值参数解决方法

c++ - 如何避免在我的代码中频繁键入 namespace::overly?

c++ - 如何在 C++\wxWidgets 中下载文件