码迷,mamicode.com
首页 > 其他好文 > 详细

构造函数、析构函数调用虚函数

时间:2015-03-02 11:26:45      阅读:142      评论:0      收藏:0      [点我收藏+]

标签:构造函数 析构函数 调用虚函数

    昨天笔试的时候碰到一个很有意思的题目,大体如下:

class Parent
{
public:
    Parent()
    {
        doit();
    }
    ~Parent()
    {
        doit();
    }
    virtual void doit()
    {
        cout << "I‘m Parent!" << endl;
    }
};
class Child: public Parent
{
public:
    Child()
    {
    }
    ~Child()
    {
    }
    void doit()
    {
        Parent::doit();
        cout << "I‘m Child!" << endl;
    }
};
int main()
{
    Parent *p_base = new Child();
    p_base->doit();
    delete p_base;
    return 0;
}

    以前在项目中并没有写过在构造函数中调用虚函数的情况,这一般也是不允许的,增加了代码的复杂度(参见Effective C++ 条款9)。这里谨记C++继承中构造、析构的顺序就不难写出答案:

I‘m Parent!
I‘m Parent!
I‘m Child!
I‘m Parent!

    但是我觉得题目应该可以出的更巧妙一些:

class Parent
{
public:
    Parent()
    {
        doit();
    }
    ~Parent()
    {
        doit();
    }
    virtual void doit()
    {
        cout << "I‘m Parent!" << endl;
    }
};
class Child: public Parent
{
public:
    Child()
    {
        doit();
    }
    ~Child()
    {
        doit();
    }
    void doit()
    {
        Parent::doit();
        cout << "I‘m Child!" << endl;
    }
};
int main()
{
    Parent *p_base = new Child();
    p_base->doit();
    delete p_base;
    return 0;
}

    如果你写下:

I‘m Parent!
I‘m Parent!
I‘m Child!
I‘m Parent!
I‘m Child!
I‘m Parent!
I‘m Child!
I‘m Parent!

    那么,恭喜你,你答错了。因为这个题目根本不会调用子类的析构函数,为啥?因为父类的析构函数是非虚函数,但是main函数中在释放的静态类型指向父类,所以它根本不调用子类的析构函数。这也是为什么在继承体系中一般都需将父类的析构函数设为虚函数(参见Effective C++ 条款7),否则有可能造成内存泄露。

     正确答案是:

I‘m Parent!
I‘m Parent!
I‘m Child!
I‘m Parent!
I‘m Child!
I‘m Parent!
I‘m Child!
I‘m Parent!


本文出自 “NeverStop” 博客,请务必保留此出处http://jlnsqt.blog.51cto.com/2212965/1616380

构造函数、析构函数调用虚函数

标签:构造函数 析构函数 调用虚函数

原文地址:http://jlnsqt.blog.51cto.com/2212965/1616380

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!