1.话不多说,我们先来看一道题:
#include<iostream>
using namespace std;
class A
{
public:
void foo()
{
printf("A::foo()\n");
}
virtual void fun()
{
printf("A::fun()\n");
}
};
class B : public A
{
public:
void foo()
{
printf("B::foo()\n");
}
void fun()
{
printf("B::fun()\n");
}
};
int main(void)
{
A a;
B b;
A *p = &a;
p->foo();
p->fun();
p = &b;
p->foo();
p->fun();
return 0;
}
那么,请问这道题的输出结果是什么呢???
分析:
(1)foo函数不是虚函数,fun是虚函数
(2)p为基类的指针,分别调用基类对象和派生类对象
结果:首先p是基类的指针,第一个指向的是基类的对象a,所以毋庸置疑当然调用的是基类的函数,所以p->foo()输出的是A::foo(),p->fun()输出的是A::fun()。而第二个则是基类的指针p指向派生类的对象,p->foo()不是虚函数,不构成多态,所以是基类指针指向一个固定偏移量函数,因此指向的是基类的函数,所以输出A::foo();而fun是虚函数,并且构成多态,因为每个含有虚函数的类都会有一个虚函数列表,所以在p->fun()函数的时候不是直接调用,而是通过虚函数列表找到相应函数的地址,因为指向的对象不同,函数地址也讲不同,所以p->fun()输出的是B::fun()。
我们来总结一下,多态到底有哪些特性呢???
多态性可以简单地概括为“一个接口,多种方法”,程序在