C++多态
什么是多态
- 通俗来说,多态就是同一个事物在不同场景下表现出来不同的状态
- 在C++中,多态体现为同一个类派生出来的对象去调用同一函数时产生了不同的行为
多态的定义及实现
在继承中构成多态的两个前提条件
1、调用函数的对象必须是指针或者引用
2、被调用的函数必须是虚函数,并且在子类中完成了对虚函数的重写
什么是虚函数?
- 虚函数就是在类的成员函数名之前加上virtual关键字
什么是虚函数的重写?
- 当派生类中有一个跟基类虚函数函数原型完全相同的函数,就称派生类的虚函数重写了基类的虚函数,完全相同指的是:函数名、参数、返回值都相同。
- 函数重写必须在两个不同的作用域中(基类和派生类中)
- 函数重写与类的访问限定符无关
- 虚函数的重写也叫做虚函数的覆盖,但是虚函数重写也有两个例外。
一个多态的实例:
class Base {
public:
virtual void testFunc() {
std::cout << "Base::testFunc()" << std::endl;
}
public:
int _b;
};
class Derived : public Base {
public:
virtual void testFunc() {
std::cout << "Derived::testFunc()" << std::endl;
}
public:
int _d;
};
void testFunc(Base& b) {
b.testFunc();
}
int main()
{
Base b;
Derived d;
testFunc(b);
testFunc(d);
system("pause");
return 0;
}
可以看到,根据函数传递对象的不同,在函数中调用的函数也是不同的,基类调用基类的函数,派生类调用派生类中的函数
虚函数重写例外之一:协变
- 虚函数重写时重写的虚函数返回值可以不同,但是必须分别是基类指针和派生类指针或者基类引用和派生类引用。此时虚函数重写我们称之为协变
一个简单协变的例子
class Base {
public:
virtual Base* testFunc() {
return new Base();
}
};
class Derived : public Base {
public:
virtual Derived* testFunc() {
return new Derived;
}
};
虚函数重写例外之二:析构函数
- 基类中的构造函数是虚函数,那么派生类的析构函数就重写了基类的析构函数,此时两个类的函数名不同,但是也构成了虚函数的重写
- 我们鼓励将析构函数写成虚函数。
在下面这种派生类中管理了资源的场景中,将析构函数写成虚函数避免了内存泄露的发生。
class Base {
public:
Base()