C++ 复制构造函数

时间:2024-09-30 09:34:56

  C++类的设计中,如果某些函数没有显式定义,C++会自动生成,复制构造函数便是其中之一,其他的还有默认构造函数、赋值操作符、默认析构函数、地址操作符。一个类的复制构造函数的原型一般为: Class_name (const Class_name &);

一、何时调用复制构造函数

  在新建一个对象并将其初始化为同类对象的时候,常常会调用复制构造函数,如:

    Class_name A(B);

    Class_name A = B ;

    Class_name A = Class_name(B);

    Class_name *p = new Class_name(A);// 用A初始化一个匿名对象,并将其地址赋予指针P

  每当程序生成对象副本时,编译器都会调用复制构造函数。具体地说,当函数按值传递对象或生成临时对象时,编译器都会调用复制构造函数。如当3个Vector对象相加时,编译器会调用复制构造函数来生成临时对象。

二、复制构造函数的浅复制

  默认的复制构造函数是浅复制,即逐个复制非静态成员数据的值。

  (1)如果类成员是另一个类的对象,那么将调用另一个对象的复制构造函数;

  (2)静态成员数据不被复制,因为它们属于整个类,而不是一个对象。

  (3)如果成员中含有含有指针P,那么它的地址也会赋给新的对象中相应的P,这样会导致两个或多个变量指向同一个指针——比较危险的一件事。

三、复制构造函数的深复制

  显式地定义复制构造函数可以有效解决浅复制的弊端。下面以一个自定义的MyString类作为例子:

C++ 复制构造函数

  假若是使用默认的复制构造函数,则程序很容易崩溃,比如当你创建了对象A,用A初始化B(A和B的str指向同一个地址),然后销毁A(此时A的str指向的内存已被收回),之后你如果想销毁B,则可能使程序崩溃。

  解决方法是显式定义复制构造函数:

  C++ 复制构造函数

  在函数中使用动态内存分配,在函数里面也可以显性改变静态数据成员的值。与new相对应,在析构函数中使用delete关键字销毁内存:

  C++ 复制构造函数

  

  //End.