关于虚函数实现多态的原理及分析.docx

  1. 1、有哪些信誉好的足球投注网站(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。。
  2. 2、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载
  3. 3、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多

关于虚函数实现多态的原理及分析

目录1、C++中如何实现多态2、虚函数实现多态的原理2.1单类继承2.2多类继承示例总结

1、C++中如何实现多态

基类中先声明一个虚函数至少有一个继承该基类的子类

2、虚函数实现多态的原理

当一个类中出现虚函数或着子类继承了虚函数时,就会在该类中产生一个虚函数表(virtualtable),虚函数表实际上是一个函数指针数组(在有的编译器作用下是链表),里面的每一个元素对应指向该类中的某一个虚函数的指针。被该类声明的对象会包含一个虚函数表指针(virtualtablepointer),指向该类的虚函数表的地址。虚函数的调用过程:当一个对象要调用到虚函数时,先将对象内存中的vptr指针(虚函数表指针)指向定义该类的vtbl(虚函数表),vtbl再寻找里面的指针指向想要调用的虚函数,从而完成虚函数的调用。

2.1单类继承

定义一个父类

classPerson{

public:

virtualvoidf(){coutusef()endl;}

virtualvoidg(){coutuseg()endl;}

virtualvoidh(){coutuseh()endl;}

父类对象其在内存中布局如下:

再定义一个子类,此时并不覆盖父类的虚函数:

classBag:publicPerson{

public:

virtualvoidi(){coutusei()endl;}

virtualvoidj(){coutusej()endl;}

可以看出虚函数表内的虚函数是按声明顺序进行排序的

父类虚函数排在子类虚函数之前

当我们把子类中的虚函数覆盖掉:(修改Bag类)

classBag:publicPerson{

public:

voidf(){coutclassBagusefunendl;}

virtualvoidi(){coutusei()endl;}

virtualvoidj(){coutusej()endl;}

子类覆盖的虚函数,放在父类原先放该虚函数的位置上。

所以当父类指针指向该子类对象时,会调用该子类的重载函数

2.2多类继承

子类没有覆盖父类的虚函数

子类的虚函数放在第一张虚函数表中,紧跟着第一个父类的虚函数

如果每个父类都有虚函数,则有几个父类就有几张虚函数表

子类覆盖父类的虚函数

父类的虚函数被子类覆盖后,则该子类对应的重载函数的位置在被覆盖的父类函数的位置上。(如果父类没有该虚函数,则不用被覆盖)

父类的虚函数被子类覆盖后,则父类指针指向该子类对象时,调用的f()便是子类中重载的f()

示例

#includeiostream

usingnamespacestd;

classPerson1{

public:

virtualvoidf(){}

virtualvoidg(){}

virtualvoidh(){}

virtual~Person1(){}

classPerson2{

public:

virtualvoidf(){}

virtualvoidg(){}

virtualvoidh(){}

voida(){//成员函数,不需要重载

coutclassPerson2endl;

virtual~Person2(){}

classPerson3{

public:

virtualvoidg(){}

virtualvoidh(){}

virtual~Person3(){}

classBag:publicPerson1,publicPerson2,publicPerson3{

public:

voidf(){

coutBagf()endl;

voidg(){

coutBagg()endl;

voida(){

coutClassBagendl;

intmain(intargc,charconst*argv[])

Person3*p3=newBag;

//p3-//P3没有成员函数f()

//多态首先得是父类有虚函数,其次是子类要定义该函数的重载

//如果父类的虚函数改为成员函数,则子类无法进行重载,即无法实现多态

文档评论(0)

152****4498 + 关注
实名认证
内容提供者

该用户很懒,什么也没介绍

1亿VIP精品文档

相关文档