当继承类对象经由一个基类指针被删除,而该基类带着一个非虚拟析构函数,其结果是,对象的继承成份没有被销毁,造成局部销毁,资源泄漏。
消除这个问题就是给基类一个virtual析构函数,此后删除继承类对象就不会出问题了。
任何类只要带有virtual函数都几乎确定应该有一个virtual析构函数。
如果类不含virtual函数,通常表示它并不意图被用来做一个基类。当类不企图被当成基类,令其析构函数为virtual往往不是个好主意。因为体积会增加。
纯虚函数导致抽象类--额就是不能被实例化的类,也就是说,你不能为抽象类创建对象,然而有时候你希望拥有抽象类,但是手上没有任何纯虚拟函数,怎么办?由于抽象类总是企图被当作一个基类来用,而又由于基类应该有过虚拟析构函数,并且由于纯虚拟函数会导致抽象类,因此解法很简单:为你希望成为抽象的那个类声明一个春训析构函数。
- class AWOV
- {
- public:
- virtual ~AWOV() = 0; //声明虚拟析构函数
- };
这个类有一个纯虚拟函数,所以他是一个抽象函数,又由于它有一个虚拟析构函数,所以你不需担心析构函数的问题。然而这里有个敲门:你必须为这个纯虚拟析构函数提供一份定义:
- AWOV::~AWOV(){}//纯虚拟析构函数的定义
析构函数的运作方式是,最深层派生的那个类其析构函数最先被调用,然后是其每个基类的析构函数被调用。编译器会在AWOV的派生类的析构函数中创建一个对~AWOV的调用动作,所以你必须为这个函数提供一份定义。如果不这样做,连接器会发出抱怨。
并非所有积累的设计目的都是为了多态用途。例如标准string和STL容器都不被设计作为基类使用,更别提多态了。某些类的设计目的是作为基类使用,但不是为了多态用途。 有些类被设计用来“经由基类接口处置继承类对象”,因此它们不需要虚拟析构函数。
1.待多态性质的基类应该声明一个虚拟析构函数。如果类带任何虚拟函数,它就应该拥有一个虚拟析构函数。
2.类的设计目的如果不是作为基类使用,或不是为了具有多态性,就不应该声明虚拟析构函数。