《第7章 继承性和派生类精选PPT.ppt》由会员分享,可在线阅读,更多相关《第7章 继承性和派生类精选PPT.ppt(56页珍藏版)》请在taowenge.com淘文阁网|工程机械CAD图纸|机械工程制图|CAD装配图下载|SolidWorks_CaTia_CAD_UG_PROE_设计图分享下载上搜索。
1、第7章 继承性和派生类第1页,本讲稿共56页n保持已有类的特性而构造新类的过程称为继承。保持已有类的特性而构造新类的过程称为继承。n在已有类的基础上新增自己的特性而产生新类的过程在已有类的基础上新增自己的特性而产生新类的过程称为派生。称为派生。n被继承的已有类称为基类(或父类)。被继承的已有类称为基类(或父类)。n派生出的新类称为派生类。派生出的新类称为派生类。7.1 基类和派生类第2页,本讲稿共56页继承与派生问题举例工具车工具车面包车面包车轿车轿车小汽车小汽车卡车卡车旅行车旅行车汽车汽车交通工具交通工具第3页,本讲稿共56页继承与派生问题举例猴子猴子老虎老虎豹豹狮狮 子子猫猫鸟鸟动物动物第
2、4页,本讲稿共56页继承与派生问题举例圆圆矩形矩形几何形状几何形状第5页,本讲稿共56页继承与派生问题举例兼职技术人员兼职技术人员销售经理销售经理管理人员管理人员销售人员销售人员雇员雇员第6页,本讲稿共56页继承与派生的目的n继承的目的:实现代码重用。继承的目的:实现代码重用。n派生的目的:当新的问题出现,原有程派生的目的:当新的问题出现,原有程序无法解决(或不能完全解决)时,需序无法解决(或不能完全解决)时,需要对原有程序进行改造。要对原有程序进行改造。第7页,本讲稿共56页n继承关系,描述了派生类与基类之间的继承关系,描述了派生类与基类之间的“是是”关系,派生类是基类中的一种,是它的关系,
3、派生类是基类中的一种,是它的具体化。具体化。n组合关系,又称包含关系,一个类中有另组合关系,又称包含关系,一个类中有另一个类中的对象,表现两者之间的一个类中的对象,表现两者之间的“有有”的的关系。关系。类与类之间的关系第8页,本讲稿共56页单重继承和多重继承单重继承和多重继承继承可分为:继承可分为:n单重继承,指生成的派生类只有一个基类。单重继承,指生成的派生类只有一个基类。n多重继承,是指生成的派生类有两个或两个多重继承,是指生成的派生类有两个或两个以上的基类。以上的基类。两者的区别仅在于所继承基类数不同两者的区别仅在于所继承基类数不同第9页,本讲稿共56页 派生类定义格式如下:派生类定义格
4、式如下:class class :;7.1.1 派生类的定义第10页,本讲稿共56页n不同继承方式的影响主要体现在不同继承方式的影响主要体现在n派生类成员派生类成员对基类成员的访问权限对基类成员的访问权限n通过通过派生类对象派生类对象对基类成员的访问权限对基类成员的访问权限n继承方式包含以下继承方式包含以下3 3种:种:publicpublic(公有的方式);(公有的方式);privateprivate(私有的方式);(私有的方式);protectedprotected(保护的方式)。(保护的方式)。n默认方式:对默认方式:对classclass来讲是来讲是privateprivate;对;对
5、structstruct来讲是来讲是publicpublic。7.1.2 派生类的三种继承方式第11页,本讲稿共56页 基类中的私有成员无论哪种继承方式在派生类中基类中的私有成员无论哪种继承方式在派生类中都是不能直接访问的。都是不能直接访问的。在公有继承方式下,基类中公有成员和保护成员在派生在公有继承方式下,基类中公有成员和保护成员在派生类中仍然是公有成员和保护成员。类中仍然是公有成员和保护成员。在私有继承方式下,基类中公有成员和保护成员在派在私有继承方式下,基类中公有成员和保护成员在派生类中都为私有成员。生类中都为私有成员。在保护继承方式下,基类中公有成员和保护成员在派在保护继承方式下,基类
6、中公有成员和保护成员在派生类中都为保护成员。生类中都为保护成员。7.1.3 基类成员在派生类中的访问权限第12页,本讲稿共56页 基类成员在派生类中访问权限基类成员在派生类中访问权限 基类私有不可访问,公有不变,私有私有,保护保护。基类私有不可访问,公有不变,私有私有,保护保护。基类中成员基类中成员公有继承公有继承私有继承私有继承保护继承保护继承私成员私成员不可访问不可访问不可访问不可访问不可访问不可访问公成员公成员公有公有私有私有保护保护保护成员保护成员保护保护私有私有保护保护第13页,本讲稿共56页7.1.4 成员访问权限的控制(1)(1)公有继承方式公有继承方式class Pointcl
7、ass Point/基类基类基类基类PointPoint类的声明类的声明类的声明类的声明public:public:/公有函数成员公有函数成员公有函数成员公有函数成员void InitP(float xx=0,float yy=0)X=xx;Y=yy;void InitP(float xx=0,float yy=0)X=xx;Y=yy;void Move(float xOff,float yOff)X+=xOff;Y+=yOff;void Move(float xOff,float yOff)X+=xOff;Y+=yOff;float GetX()return X;float GetX()re
8、turn X;float GetY()return Y;float GetY()return Y;private:private:/私有数据成员私有数据成员私有数据成员私有数据成员float X,Y;float X,Y;例例1第14页,本讲稿共56页class Rectangle:public Point /class Rectangle:public Point /派生类声明派生类声明派生类声明派生类声明 public:public:/新增公有函数成员新增公有函数成员新增公有函数成员新增公有函数成员void InitR(float x,float y,float w,float h)void
9、 InitR(float x,float y,float w,float h)InitPInitP(x,y);W=w;H=h;(x,y);W=w;H=h;/调用基类公有成员函数调用基类公有成员函数调用基类公有成员函数调用基类公有成员函数float GetH()return H;float GetH()return H;float GetW()return W;float GetW()return W;private:private:/新增私有数据成员新增私有数据成员新增私有数据成员新增私有数据成员float W,H;float W,H;例例1第15页,本讲稿共56页#include#inclu
10、de#include#includeusing namecpace std;using namecpace std;int main()int main()Rectangle rect;Rectangle rect;rect.InitR(2,3,20,10);rect.InitR(2,3,20,10);/通过派生类对象访问基类公有成员通过派生类对象访问基类公有成员通过派生类对象访问基类公有成员通过派生类对象访问基类公有成员rect.Move(3,2);rect.Move(3,2);coutrect.GetX(),rect.GetY(),coutrect.GetX(),rect.GetY(),r
11、ect.GetH(),rect.GetW()endl;rect.GetH(),rect.GetW()endl;return 0;return 0;例例1第16页,本讲稿共56页 class B:public A public:void f2();protected:int j2;private:int i2;class C:public B public:void f3();#include#include class A class A public:public:void f1();void f1();protected:protected:int j1;int j1;private:pr
12、ivate:int i1;int i1;例例2第17页,本讲稿共56页 class B:A/class默默认私有私有继承承 public:void h()coutBn;A:f;/引入本作用域引入本作用域 ;void main()B b;b.f(10);b.g();/错 b.h();#include#include class A class A public:public:void f(int i)void f(int i)coutiendl;coutiendl;void g()void g()coutAn;coutAn;(2 2)私有继承方式)私有继承方式第18页,本讲稿共56页(3)保护继
13、承方式nprotected protected 成员的特点与作用成员的特点与作用n对建立其所在类对象的模块来说,它与对建立其所在类对象的模块来说,它与 private private 成员的性质相同。成员的性质相同。n对于其派生类来说,它与对于其派生类来说,它与 public public 成员的性质成员的性质相同。相同。n既实现了数据隐藏,又方便继承,实现代既实现了数据隐藏,又方便继承,实现代码重用。码重用。第19页,本讲稿共56页 class B:protected A public:B(const char*str):A(str)void Print()coutnameendl;void
14、 main()B b(Zhang);b.Print();#include#include#include#include class A class A public:public:A(const char*str)A(const char*str)strcpy(name,str);strcpy(name,str);protected:protected:char name80;char name80;第20页,本讲稿共56页 class C:protected B public:void f4();protected:int c1;private:int c2;class D:private
15、 C public:void f5();protected:int d1;private:int d2;例例 分析下列程序,并填写不同成员在不同类的访问权限。分析下列程序,并填写不同成员在不同类的访问权限。#include#include class A class A public:public:void f1();void f1();protected:protected:int a1;int a1;private:private:int a2;int a2;class B:public A class B:public A public:public:void f2();void f2(
16、);protected:protected:void f3();void f3();private:private:int b;int b;第21页,本讲稿共56页 成成员类员类f1f1()()a1a1 a2a2f2f2()()f3f3()()b bf4f4()()c1c1 c2c2f5f5()()d1d1 d2d2类类A A(基(基类类)公公有有保保护护私私有有 类类B B(公(公继继)公公有有保保护护不不可可访访公公有有保保护护私私有有 类类C C(保(保继继)公公有有保保护护私私有有 类类D D(私(私继继)公公有有保保护护私私有有第22页,本讲稿共56页单重继承指的是仅有一个基类的派生
17、继承。单重继承指的是仅有一个基类的派生继承。猴子猴子狮子狮子虎虎猎豹猎豹猫猫鸟鸟动物动物7.2 单继承第23页,本讲稿共56页n构造函数不能继承。构造函数不能继承。n派生类的构造函数承担着对基类中数据成员初始化和对派生类的构造函数承担着对基类中数据成员初始化和对派生类自身数据成员初始化的双重任务。派生类自身数据成员初始化的双重任务。n析构函数不能继承。析构函数不能继承。n派生类的析构函数应包含着基类的析构函数,用派生类的析构函数应包含着基类的析构函数,用来释放基类中的数据成员。来释放基类中的数据成员。7.2.1 派生类的构造函数和析构函数第24页,本讲稿共56页n派生类的构造函数应该包含它的直
18、接基类的构造函数。派生类的构造函数应该包含它的直接基类的构造函数。定义格式如下:定义格式如下:():):(),1 1派生类的构造函数派生类的构造函数7.2.1 派生类的构造函数和析构函数第25页,本讲稿共56页 派生类构造函数的执行顺序如下:派生类构造函数的执行顺序如下:n 先执行基类构造函数;先执行基类构造函数;n再执行子对象的构造函数(如有子对象的话);再执行子对象的构造函数(如有子对象的话);n最后执行派生类构造函数的函数体。最后执行派生类构造函数的函数体。掌握派生类构造函数时应注意如下两点 派生类构造函数的成员初始化列表中应该显式地派生类构造函数的成员初始化列表中应该显式地包含基类中带
19、参数的构造函数,或者隐含地包含基包含基类中带参数的构造函数,或者隐含地包含基类中的默认构造函数。类中的默认构造函数。第26页,本讲稿共56页n由于析构函数不能继承,因此在派生类的析构函数中要由于析构函数不能继承,因此在派生类的析构函数中要包含它的直接基类的析构函数。包含它的直接基类的析构函数。n派生类析构函数的执行顺序如下:派生类析构函数的执行顺序如下:2 2派生类的析构函数派生类的析构函数n最后执行直接基类中的析构函数。最后执行直接基类中的析构函数。n再再执执行行子子对对象象所所在在类类的的析析构构函函数数(如如果果有有子子对对象象的的话)话)n先执行派生类析构函数的函数体先执行派生类析构函
20、数的函数体第27页,本讲稿共56页例例例例 派生类构造函数的执行顺序派生类构造函数的执行顺序派生类构造函数的执行顺序派生类构造函数的执行顺序#include#include class A class A public:public:A()A()a=0;a=0;coutDefault constructor called.aendl;coutDefault constructor called.aendl;A(int i)A(int i)a=i;a=i;coutConstructor called.aendl;coutConstructor called.aendl;A()coutDestru
21、ctor called.aendl;A()coutDestructor called.aendl;void Print()couta,;void Print()couta,;int Geta()return a;int Geta()return a;private:private:int a;int a;第28页,本讲稿共56页 void main()B bb2;bb0=B(7,8,9);bb1=B(12,13,14);for(int i=0;i2;i+)bbi.Print();class B:public Aclass B:public A public:public:B()B()b=0;b
22、=0;coutDefault constructor called.bendl;coutDefault constructor called.bendl;B(int i,int j,int k):A(i),aa(j)B(int i,int j,int k):A(i),aa(j)b=k;b=k;coutConstructor called.bendl;coutConstructor called.bendl;B()coutDestructor called.bendl;B()coutDestructor called.bendl;void Print()void Print()A:Print()
23、;A:Print();coutb,aa.Geta()endl;coutb,aa.Geta()endl;private:private:int b;int b;A aa;A aa;第29页,本讲稿共56页 class B:public A public:B()b1=b2=0;B(int i)b1=0;b2=i;B(int i,int j,int k):A(i),b1(j),b2(k)B()coutIn B.n;void Print()A:Print();coutb1,b2,;private:int b1,b2;例例例例 多层派生类构造函数和析构函数。多层派生类构造函数和析构函数。多层派生类构造函
24、数和析构函数。多层派生类构造函数和析构函数。#include#include class A class A public:public:A()A()a=0;a=0;A(int i)A(int i)a=i;a=i;A()A()coutIn A.n;coutIn A.n;void Print()void Print()couta,;couta,;private:private:int a;int a;第30页,本讲稿共56页 void main()C c1;C c2(10);C c3(10,20,30,40);c1.Print();c2.Print();c3.Print();class C:pu
25、blic Bclass C:public B public:public:C()C()c=0;c=0;C(int i)C(int i)c=i;c=i;C(int i,int j,int k,int l):B(i,j,k),c(l)C(int i,int j,int k,int l):B(i,j,k),c(l)C()C()coutIn C.n;coutIn C.n;void Print()void Print()B:Print();B:Print();coutcendl;coutcendl;private:private:int c;int c;第31页,本讲稿共56页1 1子类型子类型7.2.
26、2 7.2.2 子类型和赋值兼容规则子类型和赋值兼容规则n当一个类型至少包含了另一个类型的所有行为,则称该当一个类型至少包含了另一个类型的所有行为,则称该类型是另一个类型的子类型。类型是另一个类型的子类型。n例如,在公有继承下,派生类是基类的子类型。例如,在公有继承下,派生类是基类的子类型。n如果类型如果类型A A是类型是类型B B的子类型,则称类型的子类型,则称类型A A适应于类型适应于类型B B,这时用类型,这时用类型B B对象的操作也可以用于类型对象的操作也可以用于类型A A的对象。因的对象。因此,可以说类型此,可以说类型A A的对象就是类型的对象就是类型B B的对象。的对象。n子类型的
27、关系是不可逆的。子类型的关系是不可逆的。第32页,本讲稿共56页2.类型适应n类型适应是指两种类型之间的关系类型适应是指两种类型之间的关系nB B类型适应类型适应A A类型是指类型是指B B类型的对象能够用于类型的对象能够用于A A类型的对象所能使用的场合。类型的对象所能使用的场合。n子类型与类型适应是一致的。子类型与类型适应是一致的。第33页,本讲稿共56页n当类型当类型B B是类型是类型A A的子类型时,则满足下述的子类型时,则满足下述的赋值兼容规则。的赋值兼容规则。B B类的对象可以赋值给类的对象可以赋值给A A类的对象。类的对象。B B类的对象可以给类的对象可以给A A类对象引用赋值。
28、类对象引用赋值。B B类的对象地址值可以给类的对象地址值可以给A A类对象指针类对象指针赋值。赋值。n通过基类对象名、指针、引用只能使用从通过基类对象名、指针、引用只能使用从基类继承的成员基类继承的成员 3赋值兼容规则第34页,本讲稿共56页 class B:public A public:B()b=0;B(int i,int j):A(i),b(j)void Print()coutb,;A:Print();private:int b;void fun(A&a)couta.Geta()+2Print();fun(*pb);delete pa;例例例例 分析下列程序的输出结果,熟悉赋值兼容规则在
29、该程序中的使用。分析下列程序的输出结果,熟悉赋值兼容规则在该程序中的使用。分析下列程序的输出结果,熟悉赋值兼容规则在该程序中的使用。分析下列程序的输出结果,熟悉赋值兼容规则在该程序中的使用。#include#include class A class A public:public:A()A()a=0;a=0;A(int i)A(int i)a=i;a=i;void Print()void Print()coutaendl;coutaendl;int Geta()int Geta()return a;return a;private:private:int a;int a;第35页,本讲稿共5
30、6页轮船类轮船类水路两用车类水路两用车类汽车类汽车类7.3 多继承7.3.1 7.3.1 多继承多继承的概念的概念第36页,本讲稿共56页n多继承派生类构造函数格式如下:多继承派生类构造函数格式如下:():):(),),(),2),7.3.1 多继承的构造函数和析构函数第37页,本讲稿共56页n在多重继承派生类构造函数中,先执行基类的构造在多重继承派生类构造函数中,先执行基类的构造函数。多个基类构造函数的执行顺序取决于定义派函数。多个基类构造函数的执行顺序取决于定义派生类时规定的先后顺序,与派生类的成员初始化列生类时规定的先后顺序,与派生类的成员初始化列表中顺序无关。表中顺序无关。n派生类构造
31、函数中可以隐含着直接基类的默认构造函数。派生类构造函数中可以隐含着直接基类的默认构造函数。n多重继承派生类的析构函数中隐含着直接基类的析多重继承派生类的析构函数中隐含着直接基类的析构函数,但其执行顺序与构造函数相反。构函数,但其执行顺序与构造函数相反。7.3.1 多继承的构造函数和析构函数第38页,本讲稿共56页 class B public:B(int i)b=i;coutConstructor called.Bn;B()coutDestructor called.Bn;void Print()coutbendl;private:int b;例例例例 熟悉多重继承派生类构造函数和析构函数的用
32、法。熟悉多重继承派生类构造函数和析构函数的用法。熟悉多重继承派生类构造函数和析构函数的用法。熟悉多重继承派生类构造函数和析构函数的用法。#include#include class A class A public:public:A(int i)A(int i)a=i;a=i;coutConstructor called.An;coutConstructor called.An;A()A()coutDestructor called.An;coutDestructor called.An;void Print()void Print()coutaendl;coutaendl;private:p
33、rivate:int a;int a;第39页,本讲稿共56页 class D:public A,public B public:D(int i,int j,int k,int l):B(i),A(j),c(l)d=k;coutConstructor called.Dn;D()coutDestructor called.Dn;void Print()A:Print();B:Print();coutd,c.Getc()endl;private:int d;C c;void main()D d(5,6,7,8);d.Print();B b(2);b=d;b.Print();class Cclass
34、 C public:public:C(int i)C(int i)c=i;c=i;coutConstructor called.Cn;coutConstructor called.Cn;C()C()coutDestructor called.Cn;coutDestructor called.Cn;int Getc()int Getc()return c;return c;private:private:int c;int c;第40页,本讲稿共56页 在多重继承时,在下面两种情况情况下,可能出现派在多重继承时,在下面两种情况情况下,可能出现派生类对基类成员访问的二义性。生类对基类成员访问的二义
35、性。1 1调用不同基类中的相同成员时可能出调用不同基类中的相同成员时可能出现二义性现二义性 7.3.2 多继承的二义性第41页,本讲稿共56页 class D:public A,public B public:void g()coutDD.n;void h()B:f();void main()D d;d.A:f();d.g();d.h();例例例例 分析下列程序的输出结果分析下列程序的输出结果分析下列程序的输出结果分析下列程序的输出结果#include#include class A class A public:public:void f()void f()coutA.n;coutA.n;c
36、lass B class B public:public:void f()void f()coutB.n;coutB.n;void g()void g()coutBB.n;coutBB.n;第42页,本讲稿共56页 2 2访问共同基类的成员时可能出现二义访问共同基类的成员时可能出现二义性性 当一个派生类中有多个基类,而这些基类当一个派生类中有多个基类,而这些基类又有一个共同的基类时,访问这个公共基类又有一个共同的基类时,访问这个公共基类中的成员时,可能出现二义性。中的成员时,可能出现二义性。A AB BC CD D第43页,本讲稿共56页二义性问题举例class Bclass B public
37、:public:int b;int b;class B1:public Bclass B1:public B private:private:int b1;int b1;class B2:public Bclass B2:public B private:private:int b2;int b2;class C:public B1,public B2class C:public B1,public B2 public:public:int f();int f();private:private:int d;int d;第44页,本讲稿共56页n派生类C的对象的存储结构示意图:bb1bb2dB
38、类成员B类成员B1类成员B2类成员C类对象n有二义性:nC c;nc.bnc.B:b无二义性:无二义性:c.B1:bc.B2:b45第45页,本讲稿共56页7.4 虚基类7.4.1 7.4.1 虚基类的引入和说明虚基类的引入和说明虚基类的引入虚基类的引入 :用于有共同基类的场合用于有共同基类的场合声明声明以以virtualvirtual修饰说明基类修饰说明基类例:例:class B1:virtual public Bclass B1:virtual public B作用作用主要用来解决多继承时可能发生的对同一基类继承多次而产生主要用来解决多继承时可能发生的对同一基类继承多次而产生的二义性问题的
39、二义性问题.为最远的派生类提供维一的基类成员,而不重复产生多次拷贝为最远的派生类提供维一的基类成员,而不重复产生多次拷贝注意:注意:n在第一级继承时就要将共同基类设计为虚基类。在第一级继承时就要将共同基类设计为虚基类。第46页,本讲稿共56页虚基类举例nclass B private:int b;nclass B1:virtual public B private:int b1;nclass B2:virtual public B private:int b2;nclass C:public B1,public B2 private:float d;n下面的访问是正确的:nC cobj;nco
40、bj.b;第47页,本讲稿共56页n虚基类的派生类对象存储结构示意图:BB1B2Cb1b2dB1类成员B2类成员C类对象bB类成员48第48页,本讲稿共56页虚基类举例D1nV:int nVd:intB1:nV1:intB2:nV2:intfund():voidfun():voidB1nV1:intB2nV2:intD1nVd:intfund():void B0nV:intfun()第49页,本讲稿共56页B0B1新增成员B0B2新增成员D1新增成员B0B0B1B2D1nV,fun()50第50页,本讲稿共56页51#include#include using namecpace std;us
41、ing namecpace std;class B0class B0/声明基类声明基类声明基类声明基类B0B0 public:public:/外部接口外部接口外部接口外部接口int nV;int nV;void fun()coutMember of B0endl;void fun()coutMember of B0endl;class B1:virtual public B0 /B0class B1:virtual public B0 /B0为虚基类,派生为虚基类,派生为虚基类,派生为虚基类,派生B1B1类类类类 public:public:/新增外部接口新增外部接口新增外部接口新增外部接口i
42、nt nV1;int nV1;class B2:virtual public B0 /B0class B2:virtual public B0 /B0为虚基类,派生为虚基类,派生为虚基类,派生为虚基类,派生B2B2类类类类 public:public:/新增外部接口新增外部接口新增外部接口新增外部接口int nV2;int nV2;第51页,本讲稿共56页52class D1:public B1,public B2class D1:public B1,public B2/派生类派生类派生类派生类D1D1声明声明声明声明 public:public:/新增外部接口新增外部接口新增外部接口新增外部
43、接口int nVd;int nVd;void fund()coutMember of D1endl;void fund()coutMember of D1endl;int main()int main()/程序主函数程序主函数程序主函数程序主函数 D1 d1;D1 d1;/声明声明声明声明D1D1类对象类对象类对象类对象d1d1d1.nV=2;d1.nV=2;/使用最远基类成员使用最远基类成员使用最远基类成员使用最远基类成员d1.fun();d1.fun();第52页,本讲稿共56页7.4.2 含有虚基类的派生类构造函数n建立对象时所指定的类称为最(远)派生类。建立对象时所指定的类称为最(远)
44、派生类。n虚基类的成员是由最(远)派生类的构造函数通虚基类的成员是由最(远)派生类的构造函数通过调用虚基类的构造函数进行初始化的。过调用虚基类的构造函数进行初始化的。n在整个继承结构中,直接或间接继承虚基类的所在整个继承结构中,直接或间接继承虚基类的所有派生类,都必须在构造函数的成员初始化表中有派生类,都必须在构造函数的成员初始化表中给出对虚基类的构造函数的调用。如果未列出,给出对虚基类的构造函数的调用。如果未列出,则表示调用该虚基类的默认构造函数。则表示调用该虚基类的默认构造函数。n在建立对象时,只有最(远)派生类的构造函数调用在建立对象时,只有最(远)派生类的构造函数调用虚基类的构造函数,
45、该派生类的其他基类对虚基类构虚基类的构造函数,该派生类的其他基类对虚基类构造函数的调用被忽略。造函数的调用被忽略。第53页,本讲稿共56页#include#include using namecpace std;using namecpace std;class B0class B0/声明基类声明基类声明基类声明基类B0B0 public:public:/外部接口外部接口外部接口外部接口B0(int n)nV=n;B0(int n)nV=n;int nV;int nV;void fun()coutMember of B0endl;void fun()coutMember of B0endl;c
46、lass B1:virtual public B0class B1:virtual public B0 public:public:B1(int a):B0(a)B1(int a):B0(a)int nV1;int nV1;class B2:virtual public B0class B2:virtual public B0 public:public:B2(int a):B0(a)B2(int a):B0(a)int nV2;int nV2;例例第54页,本讲稿共56页55class D1:public B1,public B2class D1:public B1,public B2 pu
47、blic:public:D1(int a):B0(a),B1(a),B2(a)D1(int a):B0(a),B1(a),B2(a)int nVd;int nVd;void fund()coutMember of D1endl;void fund()coutMember of D1endl;int main()int main()D1 d1(1);D1 d1(1);d1.nV=2;d1.nV=2;d1.fun();d1.fun();第55页,本讲稿共56页小结n基类和派生类n派生类成员的访问权限 n派生类的构造函数和析构函数n子类型及赋值兼容规则n多重继承的二义性n虚基类第56页,本讲稿共56页