相同的方法或者函数调用为不同的对象所接受时可能导致的不同行为,这种现象称为类的多态性。具体的说,它主要表现在函数调用时,实现一种接口,多种方法,多态性是面向对象程序设计的另一个重要特征。C++支持两种多态性,编译时多态性和运行时的多态性。
编译时的多态性指的是属于某个类的不同对象,或不同环境下的同一对象,调用了名称相同的成员函数,所完成的功能却不相同,这是一种静态多态性,因为编译器在对源程序进行编译时,即可确定所要调用的是哪个函数或者,通过重载机制即可实现。
运行时多态性指的是属于某个基类的不同派生对象,在形式上调用的是继承自己基类的同一成员函数。实际上调用的却是各自派生的同名成员函数,这是一种动态多态性,因为函数名,函数参数和返回类型,都相同的情况下,编译阶段不能确定要调用的函数,只能在程序运行时确定这种多态性,这种多态性通过虚函数机制来实现。
通过公用继承方式创建的派生类,继承了基类成员及其访问权限,因此公用派生类对象可以替代基类对象,完成本来由基类对象所完成的任务。派生类对象替换基类的原则是,凡是机内出现的地方都可以用,公用派生类对象取代这种取代有以下三种情况:
1.派生类对象给基类对象赋值
2.派生类对象初始化基类对象的引用
3.使基类的指针指向派生类对象(实现虚函数的关键)
class Base
{
public:
void funpublic()
{
cout<<"基类的成员函数"<public Base
{
public:
void funpublic()
{
cout<<"派生类child1的成员函数"<public Base
{
public:
void funpublic()
{
cout <<"派生类child2的成员函数"<int main() {
Base * p1,*p2,*p3,base;
child1 obj1;
child2 obj2;
base =obj1;
base.funpublic();
Base &aliasbase=obj2;
aliasbase.funpublic();
p1=&obj1;
p2=&obj2;
p1->funpublic();
p2->funpublic();
p2=new child1;
p2->funpublic();
p3=new child2;
p3->funpublic();
return 0;
}
从前面的介绍可知,虽然派生类的成员函数可以覆盖,基类的成员函数,但只能通过对象调用成员函数来使用这种附带功能,根据派生类替换基类对象的原则,可以用基类对象指针指向其派生类对象,然后通过指针调用成员函数,但也无法调用派生类中定义的覆盖函数,为了实现多态性,也就是能够指向派生类的基类指针访问派生类中同名的覆盖成员函数,则应将基类的同名函数声明为虚函数。
虚函数是一种在基类中用virtual加以定义,并在一个或多个派生类中重新定义的成员函数,定义一个虚函数的一般形式为:
virtual<返回类型><函数名>(<形参表>){函数体};
注意:关键字virtual在基类中只使用一次,而在派生类中使用的是重载的函数名,在派生类中,重新定义虚函数是函数的值和参数要和基类中的定义一致否则就属于重载错误.
class Base
{
public:
virtual void funpublic()
{
cout<<"基类的成员函数"<public Base
{
public:
void funpublic()
{
cout<<"派生类child1的成员函数"<public Base
{
public:
void funpublic()
{
cout <<"派生类child2的成员函数"<int main() {
Base * p1,*p2,*p3,base;
child1 obj1;
child2 obj2;
base =obj1;
base.funpublic();
Base &aliasbase=obj2;
aliasbase.funpublic();
p1=&obj1;
p2=&obj2;
p1->funpublic();
p2->funpublic();
p2=new child1;
p2->funpublic();
p3=new child2;
p3->funpublic();
return 0;
}