析构函数与虚函数

析构函数与虚函数

代码一
#include<iostream>
using namespace std;
class ClxBase{
public:
    ClxBase() {};
    ~ClxBase() {cout << "Output from the destructor of class ClxBase!" << endl;};

    void DoSomething() { cout << "Do something in class ClxBase!" << endl; };
};

class ClxDerived : public ClxBase{
public:
    ClxDerived() {};
   ~ClxDerived() { cout << "Output from the destructor of class ClxDerived!" << endl; };

    void DoSomething() { cout << "Do something in class ClxDerived!" << endl; };
};
  int  main(){  
  ClxDerived *p =  new ClxDerived;
  p->DoSomething();
  delete p;
  return 0;
  }
输出一
Do something in class Derived!
Output from the destructor of class Derived!
Output from the destructor of class Base!
说明一

基类析构函数不是虚函数。main函数中使用派生类的指针操作派生类的成员。释放指针p的顺序是:

先释放派生类的资源,再释放基类的资源。

代码二
#include<iostream>
using namespace std;
class Base {
public:
    Base() {};
    ~Base() { cout << "Output from the destructor of class Base!" << endl; };

    void DoSomething() { cout << "Do something in class Base!" << endl; };
};

class Derived : public Base {
public:
    Derived() {};
    ~Derived() { cout << "Output from the destructor of class Derived!" << endl; };

    void DoSomething() { cout << "Do something in class Derived!" << endl; };
};
int  main() {
    Base* p = new Derived;
    p->DoSomething();
    delete p;
    return 0;
}
输出二
Do something in class Base!
Output from the destructor of class Base!
说明二

基类析构函数不是虚函数,在main函数中使用基类指针操作派生类的成员。释放指针p的顺序是:释放基类的资源。(调用Dosomething()也是基类的版本)

派生类的资源没有得到释放会造成内存泄漏。

public继承,基类对派生类的操作,只能影响到从基类继承下来的成员。若是基类对非继承成员操作,需要将这个函数定义成虚函数。

代码三
#include<iostream>
using namespace std;
class Base {
public:
    Base() {};
    virtual ~Base() { cout << "Output from the destructor of class Base!" << endl; };

    virtual void DoSomething() { cout << "Do something in class Base!" << endl; };
};

class Derived : public Base {
public:
    Derived() {};
    ~Derived() { cout << "Output from the destructor of class Derived!" << endl; };

    void DoSomething() { cout << "Do something in class Derived!" << endl; };
};
int  main() {
    Base* p = new Derived;
    p->DoSomething();
    delete p;
    return 0;
}
输出三
Do something in class Derived!
Output from the destructor of class Derived!
Output from the destructor of class Base!
说明三

基类的析构函数与Domething()定义为虚函数,main()函数中使用基类指针操作派生类的成员。释放指针p的顺序是,释放继承类的资源,再调用基类的析构函数。

后记

若不需要基类对派生类及其对象进行操作,则不需要虚函数,这样会增加内存开销。因为虚函数会导致类维护一个虚函数表,里边存放虚函数指针。

参考:

析构函数什么情况下要定义为虚函数?

posted @ 2020-11-16 14:53  kite97  阅读(216)  评论(0编辑  收藏  举报