面向对象编程技术第七章派生与继承精选文档.ppt

上传人:石*** 文档编号:44715206 上传时间:2022-09-22 格式:PPT 页数:53 大小:2.54MB
返回 下载 相关 举报
面向对象编程技术第七章派生与继承精选文档.ppt_第1页
第1页 / 共53页
面向对象编程技术第七章派生与继承精选文档.ppt_第2页
第2页 / 共53页
点击查看更多>>
资源描述

《面向对象编程技术第七章派生与继承精选文档.ppt》由会员分享,可在线阅读,更多相关《面向对象编程技术第七章派生与继承精选文档.ppt(53页珍藏版)》请在taowenge.com淘文阁网|工程机械CAD图纸|机械工程制图|CAD装配图下载|SolidWorks_CaTia_CAD_UG_PROE_设计图分享下载上搜索。

1、面向对象编程技术第七章派生与继承本讲稿第一页,共五十三页本章主要内容本章主要内容1.类的继承与派生的提出2.派生类的定义与相关概念3.三种基本继承方式4.派生类的构造与析构函数5.派生类的成员标示与访问6.虚基类7.赋值兼容规则本讲稿第二页,共五十三页类的继承与派生的提出类的继承与派生的提出问题:问题:1.我会使用windows98,我需要重新学习XP操作系统吗?2.我定义了一个描述点的类,如何在定义一个描述矩形的类?现实思维模式现实思维模式.WH事物发展有事物发展有其延续性!其延续性!本讲稿第三页,共五十三页类的继承与派生的提出类的继承与派生的提出继承的目的继承的目的:实现数据、代码的重用。

2、派生的目的派生的目的:当新的问题出现,原有程序无法解决(或不能完全解决)时,需要对原有数据、代码进行改造。返返 回回本讲稿第四页,共五十三页派生类的定义与相关概念派生类的定义与相关概念定定义义格格式式:class 派生类名:继承方式1 基类名1,继承方式n 基类名n成员声明;注:继承方式注:继承方式1.公有继承public2.私有继承private3.保护继承protected1.保持已有类的特性而构造新类的过程称为保持已有类的特性而构造新类的过程称为继承继承。2.在已有类的基础上新增自己的特性而产生新类的过程称为在已有类的基础上新增自己的特性而产生新类的过程称为派生派生。3.被继承的已有类称

3、为被继承的已有类称为基类基类(父类)。(父类)。4.派生出的新类称为派生出的新类称为派生类派生类(子类子类)。5.直接父类、直接父类、直接直接子类;间接父类、子类;间接父类、间接间接子类子类本讲稿第五页,共五十三页派生类的定义与相关概念派生类的定义与相关概念派生(继承)的内部实现过程:派生(继承)的内部实现过程:添加新成员添加新成员 吸收除构造、析构吸收除构造、析构函数外基类成员函数外基类成员 改造基类成员改造基类成员本讲稿第六页,共五十三页派生类的定义与相关概念派生类的定义与相关概念描述平面的一个点 矩形定义简单实例:简单实例:class pointpublic:point(int a,in

4、t b)x=a,y=b;int getx()int gety()void moveto(int a,int b)private:int x,int y;class rectangle:public pointpublic:public retangle(int x,int y,int width,int heigth):point(x,y)w=width;h=height;privated:int w,h;本讲稿第七页,共五十三页派生类的定义与相关概念派生类的定义与相关概念基类与派生类的对应关系基类与派生类的对应关系:1.单继承:派生类只从一个基类派生。2.多继承:派生类从多个基类派生。3.多

5、重派生:由一个基类派生出多个不同的派生类。4.多层派生:派生类又作为基类,继续派生新的类。本讲稿第八页,共五十三页简化的继承体系图简化的继承体系图返返 回回本讲稿第九页,共五十三页三种基本继承方式三种基本继承方式1.公有继承公有继承(public)1)基类的public和protected成员的访问属性在派生类中保持不变;基类的private成员不可访问(类内类内)2)派生类的对象只能访问基类的public成员(类外类外)本讲稿第十页,共五十三页class Apublic:int x;A(int a,int b)x=a;u=b;void prt()coutpublic x=:xendl;pri

6、vate:int u;举例举例 第一步:定义基类:第一步:定义基类:本讲稿第十一页,共五十三页举例举例 第二第二 步:定义派生类步:定义派生类class B:public Apublic:B(int a,int b,int c):A(a,b)y=c;int y;void prt()coutA:x=:A:xendl;A:prt();/cout private base A:u=A:uendl;cout B:y=:yendl;此行错误!此行错误!本讲稿第十二页,共五十三页举例举例 第三步:使用派生类第三步:使用派生类void main()B b(1,2,3);b.prt();/coutb.uend

7、l;运行结果:运行结果:A:x=:1public x=:1 B:y=:31Press any key to continueError!不可直接输出u.本讲稿第十三页,共五十三页1)派生类中:基类public和protected成员变成private成员;基类private成员不可访问。2)通过派生类的对象不能访问基类中的任何成员2.私有继承私有继承(private)如何理解?类外的问题本讲稿第十四页,共五十三页class Apublic:int x;A(int a,int b)x=a;u=b;void prt()coutpublic x=:xendl;private:int u;举例举例 第

8、一步:定义基类:第一步:定义基类:本讲稿第十五页,共五十三页举例举例 第二第二 步:定义派生类步:定义派生类class B:private Apublic:B(int a,int b,int c):A(a,b)y=c;int y;void prt()coutA:x=:A:xendl;A:prt();cout B:y=:yendl;本讲稿第十六页,共五十三页举例举例 第三步:使用派生类第三步:使用派生类void main()B b(1,2,3);b.prt();/coutb.xendl;运行结果:运行结果:A:x=:1public x=:1 B:y=:31Press any key to con

9、tinue私有数据,不可直接输出b.本讲稿第十七页,共五十三页3.保护继承保护继承(public)1)派生类中:基类的public和protected成员变成protected成员;基类的private成员不可访问2)派生类的对象不能访问基类中的任何成员本讲稿第十八页,共五十三页protected 成员举例成员举例class A protected:int x;int main()A a;/a.X=5;错误本讲稿第十九页,共五十三页protected 继承class Apublic:int x void show_private()coutprivate of As y=y;void show

10、_proteced()coutprotected of As z=z;private:int y;protected:int z;本讲稿第二十页,共五十三页class B:protected Apublic:void out_base_public()coutx=:xendl;/void out_base_private()couty=:yendl;Error!void out_base_proteced()coutz=:zendl;void main()B b;/b.x=19;Errror/b.y=19;Error/b.z=19;Errorb.out_base_public();b.out_

11、base_proteced();如何访问如何访问A中的中的X、y、z?如何输出如何输出A中的私有中的私有成员成员?间接的方式间接的方式本讲稿第二十一页,共五十三页三种继承方式之间的比较三种继承方式之间的比较返返 回回本讲稿第二十二页,共五十三页派生类的构造与析构函数派生类的构造与析构函数一、构造函数一、构造函数1.基类的构造函数不被继承,需要在派生类中自行声明2.初始化完成:1.基类成员:基类构造函数完成2.内嵌对象成员3.新增成员顺序的思考:顺序的思考:有它的现实有它的现实原形么?原形么?本讲稿第二十三页,共五十三页格式:格式:派生类名:派生类名(参数总表):基类名1(参数),基类名2(参数

12、),.基类名n(参数),内嵌对象1(参数)内嵌对象n(参数)本类成员初始化赋值语句;派生类的构造函数派生类的构造函数注意:注意:参数的顺序不重要参数的顺序不重要对比组合类的构造对比组合类的构造函数函数本讲稿第二十四页,共五十三页构造函数的调用次序构造函数的调用次序1.调用基类构造函数,调用顺序按照它们被继承时声明的顺序(从左向右)。2.调用成员对象的构造函数,调用顺序按照它们在类中声明的顺序。3.派生类的构造函数完成新增成员的初始化。注意注意:派生类的析构函数的调用次序与构造函数正好:派生类的析构函数的调用次序与构造函数正好相反相反为什么?本讲稿第二十五页,共五十三页举例举例:讨论构造函数的调

13、用次序问题讨论构造函数的调用次序问题class B1/基类B1,构造函数有参数public:B1(int i)coutconstructing B1 iendl;class B2/基类B2,构造函数有参数public:B2(int j)coutconstructing B2 jendl;class B3/基类B3,构造函数无参数public:B3()coutconstructing B3*endl;本讲稿第二十六页,共五十三页class C:public B2,public B1,public B3 public:C(int a,int b,int c,int d):B1(a),memberB

14、2(d),memberB1(c),B2(b)private:B1 memberB1;B2 memberB2;B3 memberB3;void main()C obj(1,2,3,4);认真思考并回答其输出结果?本讲稿第二十七页,共五十三页constructing B2 2constructing B1 1constructing B3*constructing B1 3constructing B2 4constructing B3*Press any key to continue本讲稿第二十八页,共五十三页对构造函数调用的讨论对构造函数调用的讨论1.基类采用缺省构造函数时:派生类构造函数可

15、以调用基类缺省构造函数。2.基类声明带形参的构造函数时,派生类传递参数给基类构造函数,完成基类成员的初始化1.自定义缺省构造函数:1.无参数 2.带缺省值2.系统默认构造函数两种情形两种情形本讲稿第二十九页,共五十三页二、析构函数二、析构函数1.析构函数也不被继承,派生类自行声明2.声明方法与一般(无继承关系时)类的析构函数相同3.不需要显式地调用基类的析构函数,系统会自动隐式调用和组合类相似本讲稿第三十页,共五十三页二、析构函数二、析构函数1.析构函数的调用次序与构造函数相反 2.自定义析构函数主要完成动态分配内存对象的释放本讲稿第三十一页,共五十三页举例:举例:class B1/基类B1声

16、明public:B1(int i)coutconstructing B1 iendl;B1()coutdestructing B1 endl;class B2/基类B2声明public:B2(int j)coutconstructing B2 jendl;B2()coutdestructing B2 endl;本讲稿第三十二页,共五十三页class B3/基类B3声明public:B3()coutconstructing B3*endl;B3()coutdestructing B3 endl;class C:public B2,public B1,public B3public:C(int a

17、,int b,int c,int d):B1(a),memberB2(d),memberB1(c),B2(b)private:B1 memberB1;B2 memberB2;B3 memberB3;本讲稿第三十三页,共五十三页void main()C obj(1,2,3,4);输出结果:输出结果:Constucting B2 2Constucting B1 1Constucting B3*Constucting B1 3Constucting B2 4Constucting B3*Destructing B3Destructing B2Destructing B1Destructing B3D

18、estructing B1Destructing B2返返 回回本讲稿第三十四页,共五十三页派生类的成员标示与访问派生类的成员标示与访问问题:问题:1.当派生类与基类中有相同成员时,如何标示与访问不同类中定义的成员?本讲稿第三十五页,共五十三页举例:举例:class B1 public:int nV;void fun();class D1:public B1 public:int nV;void fun()如何访问如何访问D1类中、对象中成员?类中、对象中成员?看下页本讲稿第三十六页,共五十三页派生类的成员标示与访问派生类的成员标示与访问同名覆盖原则同名覆盖原则当派生类与基类中有相同成员时:1

19、.若未强行指名,则通过派生类对象使用的是派生类中的同名成员。2.如要通过派生类对象访问基类中被覆盖的同名成员,应使用基类名限定。本讲稿第三十七页,共五十三页void main()D1 d1;d1.nV=1;/对象名.成员名标识,访问D1类成员,同名覆盖d1.fun();d1.B1:nV=2;/作用域分辨符标识,访问基类B1成员d1.B1:fun();本讲稿第三十八页,共五十三页派生类的成员标示与访问派生类的成员标示与访问消除二义性消除二义性 2.当多个直接基类中都从某一间接基类继承共同成员时如何标示和访问?(参见下页图)(参见下页图)问题:问题:问题越来越复问题越来越复杂啦!杂啦!看下页本讲稿

20、第三十九页,共五十三页Class B0Public:Int nvVoid fun()class B1:public B0public:int nV1;void fun1();class B2:public B0 public:int nV2;void fun2();class D1:public B1,public B2 public:int nV;void fun*()本讲稿第四十页,共五十三页派生类的成员标示与访问派生类的成员标示与访问解决解决二义性问题通过直接基类,使用作用域运算符来访问不同类中的成员参照上页图示参照上页图示 D1.B1:nv=1;D1.B2:nv=2;声明虚基类(下节介

21、绍)返返 回回本讲稿第四十一页,共五十三页虚基类虚基类1.虚基类的引入:用于直接基类有共同基类的场合,2.防止多次初始化基类成员,实现维护一份拷贝3.声明:继承时以virtual修饰说明基类例:class B1:virtual public B注意:在第一级继承时就要将共同基类设计为虚基类。注意:在第一级继承时就要将共同基类设计为虚基类。下页举例本讲稿第四十二页,共五十三页虚基类举例:虚基类举例:class B0/声明基类B0public:/外部接口int nV;void fun()coutMember of B0endl;class B1:virtual public B0 /B0为虚基类p

22、ublic:/新增外部接口int nV1;class B2:virtual public B0 /B0为虚基类派生B2类 public:/新增外部接口int nV2;本讲稿第四十三页,共五十三页class D1:public B1,public B2/派生类D1声明 public:/新增外部接口int nVd;void fund()coutMember of D1endl;存储映象存储映象虚基虚基类类本讲稿第四十四页,共五十三页void main()/程序主函数 D1 d1;/声明D1类对象d1d1.nV=2;/使用直接基类数据成员d1.fun();/使用直接基类函数成员使之虚的思想使之虚的思

23、想本讲稿第四十五页,共五十三页虚基类及其派生类构造函数虚基类及其派生类构造函数1.建立对象的类称为最远派生类2.虚基类成员由最远派生类构造函数通过虚基类构造函数进行初始化本讲稿第四十六页,共五十三页虚基类及其派生类构造函数虚基类及其派生类构造函数3.派生类在构造函数的成员初始化表中调用虚基类的构造函数。否则调用该虚基类的缺省构造函数4.C保证最远(当前)派生类的构造函数调用虚基类的构造函数,忽略其它父类对虚基类构造函数的调用避免多次构造本讲稿第四十七页,共五十三页class B0/声明基类B0 public:/外部接口 B0(int n)nV=n;int nV;void fun();class

24、 B1:virtual public B0 public:B1(int a):B0(a)int nV1;class B2:virtual public B0 public:B2(int a):B0(a)int nV2;直接基类与间接基类直接基类与间接基类定义定义本讲稿第四十八页,共五十三页class D1:public B1,public B2public:D1(int a):B0(a),B1(a),B2(a)int nVd;void fund()coutMember of D1endl;void main()D1 d1(9);d1.nV=2;d1.fun();派生类定义派生类定义返返 回回本

25、讲稿第四十九页,共五十三页赋值兼容原则赋值兼容原则一个公有派生类的对象在使用上可以被当作基类的对象,反之则禁止。具体表现在:1.派生类的对象可以被赋值给基类对象2.派生类的对象可以初始化基类的引用3.指向基类的指针也可以指向派生类的对象对比类型转换在Vc等可视化开发工具中大量使用!本讲稿第五十页,共五十三页举例举例:class B0/基类B0声明 public:void display()coutB0:display()endl;class B1:public B0 public:void display()coutB1:display()endl;class D1:public B1publ

26、ic:void display()coutD1:display()display();/对象指针-成员名 本讲稿第五十一页,共五十三页void main()/主函数B0 b0;/声明B0类对象B1 b1;/声明B1类对象D1 d1;/声明D1类对象B0*p;/声明B0类指针p=&b0;/B0类指针指向B0类对象fun(p);p=&b1;/B0类指针指向B1类对象 B0&b0ref=b1;/用派生类的对象初始化基类对象的引用fun(p);p=&d1;/B0类指针指向D1类对象fun(p);返返 回回本讲稿第五十二页,共五十三页组合类的构造函数调用组合类的构造函数调用构造函数调用顺序:构造函数调用顺序:若调用缺省构造函数(即无形参的),则内嵌对象的初始化也将调用相应的缺省构造函数。内嵌对象的构造函数声明顺序声明顺序调用本类的构造函数调用本类的析构函数内嵌对象的构造函数构造:构造:析构:析构:返返 回回本讲稿第五十三页,共五十三页

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 教育专区 > 大学资料

本站为文档C TO C交易模式,本站只提供存储空间、用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。本站仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知淘文阁网,我们立即给予删除!客服QQ:136780468 微信:18945177775 电话:18904686070

工信部备案号:黑ICP备15003705号© 2020-2023 www.taowenge.com 淘文阁