C++虚析构函数解析

  当派生类对象从内存中撤销时一般先运行派生类的析构函数,然后再调用基类的析构函数。
如果用new运算符建立的派生类的临时对象,对指向基类的指针指向这个临时对象当用delete运算符撤销对象时,系统执行的是基类的析构函数,而不是派生类的析构函数,不能彻底的“清理现场”。 解决的方法是将基类及派生类的析构函数设为虚函数,这时无论基类指针指向哪个派生类对象,系统会采用动态关联,调用相应的析构函数对对象进行清理。
 
class  Point
{
public  :
          Point(){};
          ~Point(){ std::cout <<  "Point destructor"  << std::endl; }
 
private  :
};
 
class  Circle :  public  Point
{
public  :
          Circle(){};
          ~Circle(){ std::cout <<  "Circle destructor"  << std::endl; };
 
private  :
};
 
int  _tmain (  int  argc  ,  _TCHAR *  argv [])
{
            Point  *p =  new  Circle ;
            delete  p;
          getchar();
            return  0;
}
程序运行结果如下:
C++虚析构函数解析
下面将基类的析构函数改成虚析构函数
virtual   ~Point(){ std::cout <<  "Point destructor"  << std::endl; }
其它的不变,再运行:
C++虚析构函数解析
这样就达到我们的目的了,基类,派生类都调用了析构函数,另外需要注意的是
在基类的析构函数声明为虚函数时,由该基类派生的析构函数也自动成为虚函数,即使派生类的析构函数与基类的析构函数名字不相同。
 
  程序中显示的用delete运算符删除一个对象,而这个对象是指向派生类对象的基类指针,系统调用相应派生类的析构函数。
如果程序中的局部对象离开其作用域,系统会隐式地调用其析构函数
 
咱们增加一个函数并从写main函数:
 
Point  *fc()
{
            Circle  cl;
            Point  *p =  new  Circle ;
            return  p;
}
int  _tmain (  int  argc  ,  _TCHAR *  argv [])
{
          Point  *q =  fc();
            delete  q;
          getchar();
            return  0;
}
运行结果如下:
C++虚析构函数解析
  在上例中,函数非常fc的内部定义了两个对象:c1和p所指向的Circle类对象。对象cl在函数fc结束时执行Circle的析构函数,撤销局部变量c1.p所指向的对象的地址通过函数返回值赋予q,q所指向的对象在执行delete时执行析构函数。

你可能感兴趣的:(C++)