当出现同名函数时,需要用到virtual,这样的话,就相当于取最新的那个。
虚函数及时在原来的定义函数前加virtual
//虚基类的做法,出现成员函数同名时用这个
class A{
void test(){
cout<<"A";
}
class B:public virtual A{
void test()
{
cout<<"B";
}
}
//虚函数的做法,出现有公用爷类的用这个
class A{
virtual void test(){
cout<<"A";
}
class B:public A{
void test()
{
cout<<"B";
}
}
A*p=new B();//生成一个指针,这个指针指向B的一个对象
有了virtual后,p->test();输出的就是B了
这就是virtual的作用:根据对象的实际类型,调用相应的类型函数。
如果没有virtual,那么p->test();输出的就是A了
没有virtual时,p指向test函数,那么调用的是父类的还是子类的呢?
在没有virtual的情况下,可以有两种不同的解释:
1.指针p的类型是A的*
2.指针p指向的对象是B
那么实际结果上面已经说了,是输出A
注意:
1.在父类中将函数声明为virtual,自类就自动是virtual了,当然你要两个地方都加virtual也可以。
2.即将被重写的函数添加virtual,是一条应该遵守的编码习惯
3.基类指针指向派生类对象,只能调用基类成员,但通过虚函数,可调用派生类成员(原因在“基类指针指向派生类对象”那一篇文章可见)
4.当通过基类指针删除派生类对象时候。大多数基类都至少有一个虚函数,因此,大多数情况下,在存在继承关系且基类有虚函数的时候,往往需要将基类的析构函数声明为virtual,这样做的目的是避免内存析构。
5.虚析构函数防止内存泄漏
6.构造函数不加virtual
(这些在后面都会出文章讲解的)