读《C++沉思录》心得:拷贝构造函数

  在读《C++沉思录》中第53页的下面这段代码时,突然看不懂了:

1 int num=0;
2 VehicleSurrogate parking_lot[3];
3 Automobile x;
4 parking_lot[num++]=x;
5 //最后一天语句等价于下句
6 //parking_lot[num++]=VehicleSurrogate(x);

 

  书上是这么解释上面这段的:

  •   “这个语句创建了一个关于对象x的副本,并将VehicleProxy对象绑定到该副本,然后将这个对象赋值给parking_lot的一个元素。当最后销毁parking_lot数组时,所有这些副本也被清除。”

  对于书上的这段解释,我可以理解它是解释代码中的第6行,但是完全不能理解它可以解释第4行。对于第4行,我的理解是:它调用了拷贝构造函数。之后我就在网上搜索了一下拷贝构造函数的使用,于是得出如下三处使用拷贝构造函数的地方:

  1. 一个对象以值传递的方式传入函数体 
  2. 一个对象以值传递的方式从函数返回
  3. 一个对象需要通过另外一个对象进行初始化

  而拷贝构造函数三处所使用的地方,都不能说是此时代码第4句的这种情形。就算是那也只能说第4句它肯定调用了拷贝构造函数,并且它使用的是拷贝构造函数使用情况的第三种情况。但是那个“=”是怎么回事呢,带着这种疑惑我决定亲自写代码测试一下,看能不能发现什么。

  以下为我将《C++沉思录》中的这段代码的例子简易写下来为了测试的代码:

 //class Vehicle
//Vehicle.h
1
#include<iostream> 2 using namespace std; 3 class Vehicle 4 { 5 public: 6 virtual Vehicle* copy() const=0; 7 virtual ~Vehicle() 8 { 9 cout<<"this is class Vehicle::~Vehicle()"<<endl; 10 11 } 12 };
 //class Automobile
//Automobile.h
1
#include<vehicle.h> 2 #include<iostream> 3 using namespace std; 4 class Automobile : public Vehicle 5 { 6 public: 7 Automobile(); 8 Vehicle* copy() const; 9 ~Automobile(); 10 };
 //class Automobile
//Automobile.cpp
1
#include "automobile.h" 2 3 Automobile::Automobile() 4 { 5 cout<<"this is class Automobile::Automobile()"<<endl; 6 } 7 8 Vehicle *Automobile::copy() const 9 { 10 cout<<"this is class Automobile::copy() const"<<endl; 11 return new Automobile(*this); 12 } 13 14 Automobile::~Automobile() 15 { 16 cout<<"this is class Automobile::~Automobile()"<<endl; 17 }
 //class VehicleSurrogate
//VehicleSurrogate.h
1
#include"vehicle.h" 2 #include<iostream> 3 using namespace std; 4 class VehicleSurrogate 5 { 6 public: 7 VehicleSurrogate(); 8 VehicleSurrogate(const Vehicle& v); 9 VehicleSurrogate(const VehicleSurrogate&v); 10 VehicleSurrogate&operator=(const VehicleSurrogate&v); 11 ~VehicleSurrogate(); 12 private: 13 Vehicle *vp; 14 };
 //class VehicleSurrogate
//VehicleSurrogate.cpp
1
#include "vehiclesurrogate.h" 2 3 VehicleSurrogate::VehicleSurrogate():vp(0) 4 { 5 cout<<"this is class VehicleSurrogate::VehicleSurrogate()"<<endl; 6 } 7 8 VehicleSurrogate::VehicleSurrogate(const Vehicle &v)//:vp(v.copy) 9 { 10 vp=v.copy(); 11 cout<<"this is class VehicleSurrogate::VehicleSurrogate(const Vehicle &v)"<<endl; 12 } 13 14 VehicleSurrogate::VehicleSurrogate(const VehicleSurrogate & v):vp(v.vp?v.vp->copy():0) 15 { 16 cout<<"this is class VehicleSurrogate::VehicleSurrogate(const VehicleSurrogate & v)"<<endl; 17 } 18 19 VehicleSurrogate &VehicleSurrogate::operator =(const VehicleSurrogate &v) 20 { 21 cout<<"this is class VehicleSurrogate::operator =(const VehicleSurrogate &v)"<<endl; 22 if(this!=&v) 23 { 24 delete vp; 25 vp=(v.vp?v.vp->copy():0); 26 } 27 return *this; 28 } 29 30 VehicleSurrogate::~VehicleSurrogate() 31 { 32 cout<<"this is class VehicleSurrogate::~VehicleSurrogate()"<<endl; 33 delete vp; 34 }
 //main.cpp
1
#include <iostream> 2 #include"vehiclesurrogate.h" 3 #include"vehicle.h" 4 #include"automobile.h" 5 using namespace std; 6 7 int main() 8 { 9 int num=0; 10 VehicleSurrogate parking_lot[3]; 11 Automobile x; 12 parking_lot[num++]=x; 13 //parking_lot[num++]=VehicleSurrogate(x); 14 15 return 0; 16 }

  通过对上面代码的运行,得出运行结果如下图1:

图 1

  由运行结果的第5,6,7,8行可以看出,在调用“parking_lot[num++]=x”时,函数依次执行了:

  1. VehicleSurrogate的拷贝构造函数VehicleSurrogate(const Vehicle &v);
  2. Automobile的拷贝函数copy()const;
  3. VehicleSurrogate的“=”赋值操作符operator=(const VehicleSurrogate&v);
  4. Automobile的拷贝函数copy()const;

  而将上面这句“parking_lot[num++]=x”换为“parking_lot[num++]=VehicleSurrogate(x)”时,执行的效果是一样的,见下图2:

 图 2

  至此,我们可以得出:parking_lot[num++]=x这句代码,依次执行了VehicleSurrogate的拷贝构造函数和赋值操作符。

posted on 2013-05-16 11:47  maybob  阅读(462)  评论(2编辑  收藏  举报