虚函数是针对动态多态性设计的。什么是动态多态性呢?动态多态性是指程序运行时,不在编译时确定用哪个函数,而是在程序在运行过程中才动态地确定操作所针对的对象。这一过程需要通过虚函数来实现。
虚函数,就是在基类中声明此函数是虚拟的,并不是实际存在的函数,在派生类中,需要使用的时候再重新定义此函数。
虚函数的作用就是允许在派生类中重新定义与基类中完全重名的函数,并且允许通过基类指针或引用来访问基类和派生类中的通明函数。
1.虚函数的声明:
virtual void display(){ //virtua关键字 函数类型 函数名
//函数体
}
在基类中定义虚函数后,以此类为基类的派生类中出现与虚函数同名的函数默认为虚函数,可重新定义。
class base1 {
public:
virtual void display() const; //虚函数
};
void base1::display() const{
cout << "base1::dispaly()" << endl;
}
class base2 :public base1 {
public:
void display() const;
//派生类中,基类中的虚函数根据函数名、参数列表等覆盖派生类的相应函数。
};
void base2::display() const {
cout << "base2::dispaly()" << endl;
}
class base3 :public base2 {
public:
void display() const;
//派生类中,基类中的虚函数根据函数名、参数列表等覆盖派生类的相应函数。
};
2.可以被定义为虚函数的有:普通成员函数、析构函数。注意,构造函数不能是 虚函数,必须是实打实的哈哈哈。
析构函数被定义为虚函数,被称为虚析构函数。这种函数有两个优点:
可以通过基类指针删除派生类对象;可以通过基类指针调用对象的析构函数(利用delete删除动态内存分配的空间)。
base::~base() {
cout << "Base desconstructor" << endl;
}
class derived :public base{
public:
derived();
virtual ~derived(); //虚析构函数
private:
int *p;
};
derived::derived() {
p = new int(0);
}
derived::~derived() {
cout << "Derived desconstructor" << endl;
delete p;
}
void fun(base *p) {
delete p;
}
int main() {
base *b = new derived();
fun(b);
return 0;
}
运行结果:
Derived desconstructor
Base desconstructor
3.当基类中虚函数仅有声明,而没有定义具体的操作内容,为空,要求在派生类中根据自己的实际情况定义自己的版本,这个虚函数为纯虚函数。
class 类名{
virtual 类型 函数名(参数表)=0;//纯虚函数
}
带有纯虚函数的类抽象类。