C++ 为什么我们需要c+中的复制构造函数和赋值运算符+;

C++ 为什么我们需要c+中的复制构造函数和赋值运算符+;,c++,C++,复制构造函数和赋值操作符都是从一个对象复制到另一个对象,那么为什么我们需要两者呢? Copyconstructor意味着它创建一个新对象并从另一个现有对象复制内容,赋值运算符将内容从一个现有对象复制到现有对象 因此,最终两者都是将内容从一个对象复制到另一个对象,那么为什么我们需要两者?我们只能拥有一个权限。您不应该创建虚拟对象只是为了在下一步中执行分配,每次您都需要复制 尤其是当对象构造非常昂贵时,即使在默认构造的情况下也是如此 但复制c'tors的最终原因是,用户定义类型的传递值是不可能的。然

复制构造函数和赋值操作符都是从一个对象复制到另一个对象,那么为什么我们需要两者呢? Copyconstructor意味着它创建一个新对象并从另一个现有对象复制内容,赋值运算符将内容从一个现有对象复制到现有对象


因此,最终两者都是将内容从一个对象复制到另一个对象,那么为什么我们需要两者?我们只能拥有一个权限。

您不应该创建虚拟对象只是为了在下一步中执行分配,每次您都需要复制

尤其是当对象构造非常昂贵时,即使在默认构造的情况下也是如此

但复制c'tors的最终原因是,用户定义类型的传递值是不可能的。然后我们就没有RAII了

至于赋值操作符,想象一下在没有赋值操作符的情况下编写类。通用(模板)代码看起来如何

许多泛型算法可以对仅可赋值的类进行操作,但如果没有该特性,您必须在再次“构造”对象之前自己调用它们的d'tor

template <calls T)
void assign(T& a, T& b)
{
  a.~T();
  new (&a) (b);
}

模板因为构造和赋值是不同的事情。涉及复制构造函数,例如,当您通过值传递参数或使用另一个参数构造对象时:

f(T o) {
...}

T object;
f(object); // copy construction to pass the argument
T object2(object); // construct a T from another T
当您已经拥有两个对象并希望将其中一个复制到另一个对象时,即为“指定”:

T object;
...
T object2;
...
object = object2;

这些事情发生在不同的表达式中。

这里有两种不同的情况

  • 使用现有对象的内容初始化新对象(1)
  • 将现有对象的内容复制/传输到另一个现有对象(2)
(1)
适用和
(2)
适用的情况下,存在不同的情况。它们不一样

例如,如果我们想将一个对象拥有的资源(例如内存)的所有权与另一个具有相同类型的对象共享(shared_ptr就是一个很好的例子),我们需要在该类上实现一个适当的
复制分配
操作符


因此,我们需要提供副本构造和副本分配

因为它们是不同的东西

当您要从另一个对象构造新对象时,将调用Copy ctor


当您要从另一个对象分配现有对象时,将调用赋值运算符,这意味着您可能需要在执行赋值之前销毁/释放现有对象保留的某些资源。

如果该语言设计为使用复制重构而不是赋值,则在重构之前可能需要销毁该对象。赋值运算符可以执行析构函数的操作,然后执行构造函数的操作。或者赋值操作符可以跳过其中的一些,或者以其他方式在更少的工作中获得相同的效果。我认为简单的答案是,复制构造函数确实需要在那里,或者传递值不起作用,其他事情也不起作用。赋值运算符,您可能不需要强制执行,但在某些情况下,如果您能够使其过载,您可以走得更快,所以我们来。。。此外,赋值运算符应该是什么并不总是很清楚。有时你只希望它是
memcpy
,但如果你的对象是一个智能指针,那么你就会变成一只悲伤的熊猫。如果它总是“销毁并复制构造”,那么您想要
memcpy
的情况就会变慢。