也谈析构:析构函数什么时候被调用

为何要说“也”?用google搜索“析构函数”是,google会说“约有81,500项符合 析构函数 的查询结果”,我最近复习c++是有所心得,因此“也”想谈谈“析构函数”。我不想像教科书似的介绍它,而是从它什么时候被调用来浅谈一下。java

析构函数在下边3种状况时被调用:
1.对象生命周期结束,被销毁时;
2.delete指向对象的指针时,或delete指向对象的基类类型指针,而其基类虚构函数是虚函数时;
3.对象i是对象o的成员,o的析构函数被调用时,对象i的析构函数也被调用。ios

状况1请看下边代码:
#include<iostream.h>
class A
{
 public:
 A()
 {
  cout<<"constructing A"<<endl;
 } 
 ~A()
 {
  cout<<"destructing A"<<endl;
 }
 private:
 int a;
};
class B: public A
{
 public:
 B()
 {
  cout<<"constructing B"<<endl;
 }
 ~B()
 {
  cout<<"destructing B"<<endl;
 }
 private:
 int b;
};c++

void main()
{
 B b;
}函数

运行结果为:测试

constructing A
constructing B
destructing B
destructing Agoogle

上述代码还说明了一件事:析构函数的调用顺序与构造函数的调用顺序相反。指针

状况2则正好说明了为何基类应该把析构函数声明为虚函数,请先看下边的例子:对象

#include<iostream.h>
class A
{
 public:
 A()
 {
  cout<<"constructing A"<<endl;
 } 
 ~A()
 {
  cout<<"destructing A"<<endl;
 }
 private:
 int a;
};
class B: public A
{
 public:
 B()
 {
  cout<<"constructing B"<<endl;
 }
 ~B()
 {
  cout<<"destructing B"<<endl;
 }
 private:
 int b;
};生命周期

void main()
{
 A* a = new B;
 delete a;
}io

运行结果为:

constructing A
constructing B
destructing A

若将class A中的析构函数声明为虚函数,运行结果将变成:

constructing A
constructing B
destructing B
destructing A

由此还能够看出虚函数仍是多态的基础,才c++中没有虚函数就没法实现多态。由于不声明成虚函数就不能“推迟联编”,因此不能实现多态。这点上和java不一样,java老是“推迟联编”的,因此也剩了这些麻烦。

扯远了,再看状况3,经过下边代码表示:
#include<iostream.h>
class A
{
 public:
 A()
 {
  cout<<"constructing A"<<endl;
 }
 ~A()
 {
  cout<<"destructing A"<<endl;
 }
 private:
 int a;
};

class C
{
 public:
 C()
 {
  cout<<"constructing C"<<endl;
 }
 ~C()
 {
  cout<<"destructing C"<<endl;
 }
 private:
  int c;
};

class B: public A
{
 public:
 B()
 {
  cout<<"constructing B"<<endl;
 }
 ~B()
 {
  cout<<"destructing B"<<endl;
 }
 private:
 int b;
 C c;
};

void main()
{
 B b;
}

运行结果为:

constructing A
constructing C
constructing B
destructing B
destructing C
destructing A

b的析构函数调用以后,又调用了b的成员c的析构函数,同时再次验证了析构函数的调用顺序与构造函数的调用顺序相反。

若将上边的代码中的main()函数内容改为

 A* a = new B;
 delete a;
 
由状况2咱们知道,这将不会调用class B的析构函数不会被调用,因此class C的析构函数也不会被调用。
正如咱们想的,运行结果为:

constructing A
constructing C
constructing B
destructing A

俗话说温故而知新,我却不想作什么师,只是但愿可以和你们分享一下对析构函数和虚析构函数的更深的认识。以上代码在VC++6.0上测试经过,若有疏漏或错误的认识请你们指正:)  

相关文章
相关标签/搜索