多态

多态在C++中是经过虚函数实现的,经过前面的模型【参见“有重写的单继承”】知道,若是类中有虚函数,编译器就会自动生成一个虚函数表,对象中包含一个指向虚函数表的指针,可以实现多态的关键在于:虚函数时容许被派生类重写的,在虚函数表中,派生类函数对覆盖基类函数。初次以外,还必须经过指针或引用调用方法才行,将派生类对象赋给基类对象。ide

wKioL1fIGVSiUANmAAAerJGMzkg291.png-wh_50

上面两个类,基类派生类中都包含两个方法函数

void print() const;
virtual void print_virtual() const;

这两个方法的区别就是一个是普通成员函数,一个是虚函数,编写代码以下指针

void test_polmorphisn()
{
Base b;
Derived d;

b = d;
b.print();
b.print_virtual();

Base *p;
p = &d;
p->print();
p->print_virtual();
}

根据模型推测,只有p->print_virtual()才实现了动态,其余3调用基类方法,缘由以下:对象

1)b.print();b,print_virtual();不能实现多态是由于经过基类对象调用,而非指针或引用因此不能实现多态。blog

2)p->print();不能实现多态是由于,print函数没有生命为虚函数,派生类中也定义了print函数知识隐藏了基类的print函数。继承

为何析构函数设为虚函数是不要的?get

析构函数应当都是虚函数,除非明确该类不作基类(不被其余类继承),基类的析构函数声明为虚函数,这样作是为了确保释放派生类对象时,按照正确的顺序调用析构函数。编译器

从C++对象模型能够知道,若是析构函数不定义为虚函数,那么派生类就不会重写基类的析构函数,在有多态行为的时候,派生类的析构函数不会被调用到。it

例如,经过new一个派生类对象,赋给基类指针,而后delete基类指针io

void test_vitual_destructor()
{
Base *p = new Derived();
delete p;
}

若是基类函数不是析构函数

wKioL1fIHaexEGrzAAAD06ojXos045.png

注意,缺乏派生类的析构函数调用,把析构函数声明为虚函数,调用就正常了

wKioL1fIHePxet6sAAADmUkNJzs794.png

相关文章
相关标签/搜索