发布网友 发布时间:2024-10-24 09:42
共1个回答
热心网友 时间:2024-11-06 18:54
为了解决继承中的二义性问题,提出了虚基类和虚继承。虚继承主要解决具有公共祖先的多继承带来的二义性问题,对于没有公共祖先的多继承则无法解决。
多态性是面向对象程序设计语言中数据抽象和继承之外的第三个基本特征。它提供接口与具体实现之间的隔离,将“what”和“how”分离开来,从而提高了代码的可读性和组织性,并使程序具有可扩展性。C++支持编译时多态(静态多态)和运行时多态(动态多态),运算符重载和函数重载属于编译时多态,而派生类和虚函数则实现运行时多态。
静态多态和动态多态的区别在于函数地址的绑定时间。如果函数调用在编译阶段就能确定调用地址并产生代码,这就是静态多态(编译时多态),意味着地址是早绑定的。而如果函数调用地址不能在编译期间确定,需要在运行时才能决定,那么这属于晚绑定(动态多态,运行时多态)。向上类型转换是指对象可以作为自己的类或者作为其基类的对象来使用,还可以通过基类的地址来操作它。取一个对象的地址(指针或引用),并将其作为基类的地址来处理,这种称为向上类型转换。也就是说:父类引用或指针可以指向子类对象,通过父类指针或引用来操作子类对象。
C++动态多态性是通过虚函数实现的,虚函数允许子类(派生类)重新定义父类(基类)成员函数,子类重新定义父类虚函数的做法称为覆盖(override)或重写。在设计时,常常希望基类仅作为其派生类的一个接口。仅想对基类进行向上类型转换,使用它的接口,而不希望用户实际创建一个基类的对象。同时,创建一个纯虚函数允许接口中放置成员原函数,而不一定要提供一段可能对这个函数毫无意义的代码。
为了实现这一点,可以在基类中加入至少一个纯虚函数(pure virtual function),使得基类成为抽象类(abstract class)。纯虚函数使用关键字virtual,并在其后面加上=0。如果试图实例化一个抽象类,编译器则会阻止这种操作。当继承一个抽象类时,必须实现所有的纯虚函数,否则由抽象类派生的类也是一个抽象类。Virtual void fun() = 0;告诉编译器在vtable中为函数保留一个位置,但在这个特定位置不放地址。
虚析构函数是为了解决基类的指针指向派生类对象,并用基类的指针删除派生类对象的问题。纯虚析构函数在C++中是合法的,但在使用时有一个额外的:必须为纯虚析构函数提供一个函数体。纯虚析构函数和非纯析构函数之间唯一的不同之处在于纯虚析构函数使得基类成为抽象类,不能创建基类的对象。