电子文档交易市场
安卓APP | ios版本
电子文档交易市场
安卓APP | ios版本

多态性与虚函数课件

36页
  • 卖家[上传人]:F****n
  • 文档编号:88149510
  • 上传时间:2019-04-20
  • 文档格式:PPT
  • 文档大小:169.50KB
  • / 36 举报 版权申诉 马上下载
  • 文本预览
  • 下载提示
  • 常见问题
    • 1、C+程序设计,第8章(2) 多态性与虚函数,主要内容,C+的多态性 动态多态性的实现条件 虚函数的声明 虚函数的特性与调用 静态关联、动态关联 虚析构函数 纯虚函数 抽象类 综合实例,C+的多态性,多态性:指对不同类型的对象发送同样的消息(即调用同名的函数),不同类型的对象在接收时会产生不同的行为(即执行各自同名的函数)。 编译时多态性(静态多态性):指在编译阶段,系统就可根据所操作的对象,确定其具体的操作。编译时多态性是通过函数重载、运算符重载来实现的。函数重载是根据函数调用式中所给出的实参的类型或实参的个数,在编译阶段系统就可确定调用的是同名函数中的哪一个。运算符重载是根据运算式中所给出的运算对象的类型,在编译阶段系统就可确定执行的是同种运算中的哪一个。 运行时多态性(动态多态性):指在编译阶段,系统仅根据函数调用式是无法确定调用的是同名函数中的哪一个;必须在程序运行过程中,动态确定所要调用函数的当前对象,并根据当前对象的类型来确定调用的是同名函数中的哪一个。 运行时多态性是通过 “类的继承关系” 加上 “虚函数” 联合起来实现的。,动态多态性的实现条件,要有类的继承层次结构:一个

      2、基类可以派生出不同的派生类,各派生类中可以新增与基类中的函数名字相同、参数个数及类型也相同的成员,这些同名的成员函数在不同的派生类中就有不同的含义!这样,在类的继承结构中,不同的层次上出现了名字相同、参数个数及类型也相同、但功能不同的函数! 引入虚函数:作用是在由一个基类派生出的类体系中实现 “一个接口,多种方法”,主要用于建立通用程序。对于同一类体系中的各层次派生类,使用虚函数可实现统一的类接口,以便用相同的方式对各层次派生类的对象进行操作。虚函数是基类的成员函数,是为了实现某一种功能而假设的虚拟函数,在该基类的各层次派生类中对该虚函数可有各自不同的定义 ! 要能体现虚函数的特性:必须通过基类的对象指针、基类的对象引用来调用各层次派生类对象的同名虚函数,才能体现虚函数的特性!因为只有这样才能用相同的调用方式去调用不同层次派生类对象的同名虚函数,从而实现动态多态性。,虚函数的声明,虚函数的声明:class 基类 virtual 返回值类型 成员函数名 ( 形参表 ) 函数体 ; 当一个基类的某成员函数声明为虚函数,则在该基类的所有派生类中,与虚函数同名、参数个数及类型相同、且返回值类型

      3、也相同的,不论是否有关键字 virtual 修饰,都是虚函数,反之不然。但要注意:若在派生类中只是与虚函数同名,而参数个数或类型有不同时,属于函数重载,不是虚函数! virtual 只是用在类中声明虚函数,若在类外定义虚函数前面不要加 virtual。 构造函数、静态成员函数不能声明为虚函数!析构函数可以声明为虚函数。,虚函数的特性与调用,如何体现虚函数的特性?只有通过基类的对象指针、基类的对象引用来调用派生类对象的虚函数时,才能体现虚函数的特性!而通过派生类对象的对象名、对象指针、对象引用来调用虚函数时,无法体现虚函数的特性! 派生类对象中一般成员函数的调用方法: 可通过派生类对象的对象名、对象指针、对象引用来调用!调用过程:若派生类新增成员函数中存在该函数,则被调用;若不存在,则调用上一层基类中的该函数;若这一层基类中也不存在,就继续往上一层寻找 ,直至找到该函数并被调用。 派生类对象中一般成员函数的调用方法: 可通过基类的对象指针、基类的对象引用来调用派生类对象中的一般成员函数!但只能调用派生类中从该基类继承过来的那部分成员函数!,虚函数的特性与调用,派生类对象中虚函数的调用方法

      4、: 派生类对象的虚函数也是成员函数,可按一般成员函数的方式调用!即:可通过派生类对象的对象名、对象指针、对象引用来调用!调用过程与一般成员函数的调用过程相同!由此可见,这种调用方式无法体现虚函数的特性! 派生类对象中虚函数的调用方法: 可通过基类的对象指针、基类的对象引用来调用派生类对象的虚函数!调用过程:调用的是派生类中的虚函数!若派生类中没有重新定义该虚函数,则调用的是上一层基类中的该虚函数;若在这一层基类中也没有重新定义该虚函数,就继续往上一层寻找 ,直至基类的对象指针、基类的对象引用它们本身所属的那一层基类! 动态多态性的实现:可以让基类的对象指针(或基类的对象引用)先后指向(或先后引用)同一类族中不同派生类的对象,以便用相同的调用方式去调用不同派生类对象中的同名虚函数,从而实现动态多态性。,【例】(派生类对象中一般成员函数的调用方法:可通过派生类对象的对象名、对象指针、对象引用来调用!注意调用过程。) # include class A int x ; public: A ( int a ) x = a ; void g( ) cout f( ) ; pd-g( ) ; D

      5、,【例】(派生类对象中虚函数的调用方法:可通过派生类对象的对象名、对象指针、对象引用来调用!注意调用过程与一般成员函数相同!由此可见,这种调用方式无法体现虚函数的特性!) # include class A int x ; public: A ( int a ) x = a ; virtual void g( ) cout f( ) ; pd-g( ) ; D ,【例】(派生类对象中一般成员函数的调用方法:可通过基类的对象指针、基类的对象引用来调用!但只能调用派生类中从该基类继承来的那部分成员函数!) # include class A int x ; public: A ( int a ) x = a ; void g( ) cout g( ) ; aa1. g( ) ; /pa-f( ); 为什么不行? B *pb = ,【例】(派生类对象中虚函数的调用方法:可通过基类的对象指针、基类的对象引用来调用!注意:调用的是派生类中的虚函数!若派生类中没有重新定义该虚函数,则调用的是上一层基类中的该虚函数, ) # include class A int x ; public: A ( i

      6、nt a ) x = a ; virtual void g( ) cout g( ) ; aa1. g( ) ; /pa-f( ); 为什么不行? B *pb = ,【例】(请注意调用过程。) # include class A int x ; public: A ( int a ) x = a ; virtual void g( ) cout g( ) ; aa1. g( ) ; /pa-f( ); 为什么不行? B *pb = ,【例】 (请注意调用过程。) # include class A int x ; public: A ( int a ) x = a ; void g( ) cout g( ) ; aa1. g( ) ; /pa-f( ); 为什么不行? B *pb = ,【例】(注意,若派生类中的某函数只是与虚函数同名,但参数个数或类型有不同时,则属于函数的重载,而不是虚函数!) # include class A int x ; public: A ( int a ) x = a ; virtual void g( ) cout g( ) ; aa1. g( ) ;

      7、/pa-f( ); 为什么不行? B *pb = ,【例】(动态多态性的实现:可以让基类的对象指针,先后指向同一类族中不同派生类的对象,这样就可以用相同的调用方式去调用不同派生类对象中的同名虚函数,从而实现动态多态性。) # include class A int x ; public: A ( int a=0 ) x = a ; cout “调用A类构造了!n” ; virtual void show( ) cout “A类 x=” x endl ; ; class B : public A int y ; public: B ( int a=0, int b=0 ) : A( a ) y = b ; cout “调用B类构造了!n” ; void show( ) cout “B类 y=” y endl ; ; class C : public B int z ; public: C( int a=0, int b=0, int c=0 ) : B( a, b ) z = c ; cout “调用C类构造了!n” ; void show( ) cout “C类 z=” z endl

      8、; ;,void main ( ) A a1( 1 ) ; B b1( 20, 30 ) ; C c1( 400, 500, 600 ) ; A *p ; p = ,静态关联、动态关联,关联(绑定、联编):指程序自身彼此关联的过程,即程序中不同部分互相绑定的过程,以确定程序中的各个函数调用式与所执行的相应函数代码的关系,简单的说,关联就是把某个标识符与某个存储地址联系起来。 静态关联(静态绑定、静态联编):指关联(绑定、联编)工作出现在编译阶段。例如,程序中使用对象名来调用成员函数时,在编译阶段系统就能根据对象的类型确定所要调用的是哪一个类的成员函数并进行关联。再如,使用对象名来调用某个类族中的虚函数时,在编译阶段系统也能确定要调用的虚函数属于哪一个类并进行关联。 此外,函数重载和运算符重载也是在编译阶段进行关联的。 动态关联(动态绑定、动态联编):指绑定(联编、关联)工作出现在运行阶段。例如,程序中使用基类的对象指针(或基类的对象引用)来调用某个类族中的虚函数时,只有在程序运行过程中,才能根据其具体指向(或具体引用)该类族中的哪一个类的对象,确定出调用的是哪一个类的虚函数。,静态关联

      9、、动态关联,虚函数的动态关联:只有通过基类的对象指针(或基类的对象引用)来调用同一类族中派生类的虚函数时,才属于动态关联!原因是:只有在程序运行过程中,系统才能根据该指针(或该引用)具体指向(或具体引用)的是同一类族中的哪一个派生类的对象,确定出调用的是哪一个派生类的虚函数。 注意: 虚函数与一般成员函数比较,调用时执行速度要慢一些。使用虚函数,系统要有一定的空间和时间开销。 当一个类中有虚函数时,编译系统会为该类构造一个虚函数表,它是一个指针数组,存放该类的每个虚函数的入口地址。 由于虚函数的调用机制是间接实现的,且动态关联是在程序运行阶段,相对会降低程序的运行效率。 但通用性也是程序追求的主要目标之一。 虚函数必须是非静态的成员函数:因为静态成员函数不受限于某个对象。,【例】(分别通过对象名、基类的对象指针去调用派生类的虚函数。) # include class A int x ; public: A ( ) x = 10 ; virtual void show( ) cout show( ) ; p = /此处调用属于动态关联! ,【例】(在成员函数中调用虚函数:关键是分析在调用该成员函数时,其 this 指针是基类的对象指针还是派生类的对象指针! ) # include class A public: virtual void f1( ) cout f2( ); void f2( ) cout f3( ); virtual void f3( ) cout f4( ); virtual void f4( ) cout f5( ); void f5( ) cout f4( ); void f4( ) cout f5( ); void f5( ) cout “B:f5n” ; ; v

      《多态性与虚函数课件》由会员F****n分享,可在线阅读,更多相关《多态性与虚函数课件》请在金锄头文库上搜索。

      点击阅读更多内容
    最新标签
    发车时刻表 长途客运 入党志愿书填写模板精品 庆祝建党101周年多体裁诗歌朗诵素材汇编10篇唯一微庆祝 智能家居系统本科论文 心得感悟 雁楠中学 20230513224122 2022 公安主题党日 部编版四年级第三单元综合性学习课件 机关事务中心2022年全面依法治区工作总结及来年工作安排 入党积极分子自我推荐 世界水日ppt 关于构建更高水平的全民健身公共服务体系的意见 空气单元分析 哈里德课件 2022年乡村振兴驻村工作计划 空气教材分析 五年级下册科学教材分析 退役军人事务局季度工作总结 集装箱房合同 2021年财务报表 2022年继续教育公需课 2022年公需课 2022年日历每月一张 名词性从句在写作中的应用 局域网技术与局域网组建 施工网格 薪资体系 运维实施方案 硫酸安全技术 柔韧训练 既有居住建筑节能改造技术规程 建筑工地疫情防控 大型工程技术风险 磷酸二氢钾 2022年小学三年级语文下册教学总结例文 少儿美术-小花 2022年环保倡议书模板六篇 2022年监理辞职报告精选 2022年畅想未来记叙文精品 企业信息化建设与管理课程实验指导书范本 草房子读后感-第1篇 小数乘整数教学PPT课件人教版五年级数学上册 2022年教师个人工作计划范本-工作计划 国学小名士经典诵读电视大赛观后感诵读经典传承美德 医疗质量管理制度 2 2022年小学体育教师学期工作总结 2022年家长会心得体会集合15篇
    关于金锄头网 - 版权申诉 - 免责声明 - 诚邀英才 - 联系我们
    手机版 | 川公网安备 51140202000112号 | 经营许可证(蜀ICP备13022795号)
    ©2008-2016 by Sichuan Goldhoe Inc. All Rights Reserved.