面向对象程序设计语言C---精品课模板cs.ppt
第七章第七章 类与对象类与对象丘志杰丘志杰电子科技大学电子科技大学计算机学院计算机学院 软件学院软件学院C+与与C最最大大的的不不同同在在于于C+增增加加了了面面向向对对象象的的概概念念。C+允允许许用用户户定定义义新新的的抽抽象象数数据据类类型型类类类类型型,它它将将一一组组数数据据和和与与这这些些数数据据相相关关的的操操作作封封装装在在一一起起,实实现现了了面面向向对对象象技技术术中中的的核核心概念心概念数据封装数据封装。2023/2/92抽象是对具体对象(问题)进行概括,抽象是对具体对象(问题)进行概括,抽出这一类对象的抽出这一类对象的公共性质公共性质并加以描述并加以描述的过程。的过程。先注意问题的本质及描述,其次是实现过先注意问题的本质及描述,其次是实现过程或细节。程或细节。数据抽象:描述某类对象共有的属性或状数据抽象:描述某类对象共有的属性或状态。态。行为抽象:描述某类对象共有的行为特征行为抽象:描述某类对象共有的行为特征或具有的功能。或具有的功能。抽象抽象2023/2/93抽象实例抽象实例:时钟:时钟数据抽象:数据抽象:具有表明当前时间的具有表明当前时间的时、分、秒时、分、秒行为抽象:行为抽象:具有具有设置时间设置时间和和显示时间显示时间两个最两个最基本的功能基本的功能2023/2/94抽象实例抽象实例:人人数据抽象:数据抽象:姓名、年龄、性别等姓名、年龄、性别等行为抽象:行为抽象:生物属性:吃饭、穿衣、睡觉、行走等行为生物属性:吃饭、穿衣、睡觉、行走等行为社会属性:工作、学习等行为社会属性:工作、学习等行为2023/2/95在研究问题时,侧重点不同,可能会产生在研究问题时,侧重点不同,可能会产生不同的抽象结果;解决同一问题时要求不不同的抽象结果;解决同一问题时要求不同,也会产生不同的抽象结果。例如:同,也会产生不同的抽象结果。例如:如果开发一个人事管理软件,那么关心的是员工的如果开发一个人事管理软件,那么关心的是员工的姓名、性别、工龄、工资、工作部门等相关信息。姓名、性别、工龄、工资、工作部门等相关信息。如果开发学籍管理软件,那么关心的是学生的姓名、如果开发学籍管理软件,那么关心的是学生的姓名、性别、年龄、籍贯、所在学院等相关信息。性别、年龄、籍贯、所在学院等相关信息。因此,抽象是相对,而非绝对的。因此,抽象是相对,而非绝对的。2023/2/96如何实现抽象?如何实现抽象?抽象定义了一个事物的本质特征,那么抽象定义了一个事物的本质特征,那么从软件设计的角度又如何对抽象出来的从软件设计的角度又如何对抽象出来的结果进行描述呢?结果进行描述呢?封装可以实现抽象。封装可以实现抽象。封装就是将封装就是将数据和操作这些数据的函数数据和操作这些数据的函数进行有机地结合。进行有机地结合。C+的解决方案:的解决方案:用类来实现封装机制用类来实现封装机制2023/2/97定义和使用类的基本过程定义和使用类的基本过程第一步:进行抽象第一步:进行抽象第二步:定义类第二步:定义类第三步:实现类第三步:实现类第四步:使用类第四步:使用类2023/2/98类的定义:类的成员构成类的定义:类的成员构成class ClassName数据成员数据成员函数成员函数成员;类是一种抽象数据类型,声明形式如下:类是一种抽象数据类型,声明形式如下:关键字关键字class用于声用于声明一个类类型明一个类类型用于表达数据抽象用于表达数据抽象用于表达行为抽象用于表达行为抽象2023/2/99类定义举例:时钟类类定义举例:时钟类class Clockint Hour,Minute,Second;void SetTime(int h,int m,int s);void ShowTime();2023/2/910类成员的访问控制类成员的访问控制什么是什么是“类内类内”和和“类外类外”在类定义之内称为类内在类定义之内称为类内在类定义之外称为类外在类定义之外称为类外数据封装的目的就是数据封装的目的就是信息隐蔽信息隐蔽。为了达到信。为了达到信息隐蔽,在息隐蔽,在C+类中,并非所有的成员都是类中,并非所有的成员都是对外可见的(或者说,是类外可以访问的)。对外可见的(或者说,是类外可以访问的)。通过设置成员的通过设置成员的访问控制属性访问控制属性来实现对类成来实现对类成员的访问控制。这些控制属性有:员的访问控制。这些控制属性有:public、protected、private2023/2/911类的定义:对成员的访问控制类的定义:对成员的访问控制class ClassNamepublic:公有成员公有成员protected:保护成员保护成员private:私有成员私有成员;2023/2/912公有成员公有成员在关键字在关键字public后面声明,它们是类与后面声明,它们是类与外部的接口,任何外部的接口,任何类内、类外类内、类外函数函数都可都可以访问公有数据和函数。以访问公有数据和函数。class Clockpublic:void SetTime(int h,int m,int s);/公有成员函数公有成员函数 void ShowTime();/公有成员函数公有成员函数;2023/2/913私有成员私有成员在关键字在关键字private后面声明,后面声明,只允许本只允许本类中的函数(类中的函数(即类内函数即类内函数)访问,而类)访问,而类外的任何函数都不能访问。外的任何函数都不能访问。class Clockprivate:int Hour,Minute,Second;/私有数据成员私有数据成员;2023/2/914保护成员保护成员在关键字在关键字protected后面声明后面声明的数据成的数据成员或成员函数。与员或成员函数。与private类似,其差别类似,其差别表现在继承与派生时对派生类的影响不表现在继承与派生时对派生类的影响不同,在第八章中再描述。同,在第八章中再描述。2023/2/915类定义举例:时钟类类定义举例:时钟类class Clockpublic:void SetTime(int h,int m,int s);void ShowTime();private:int Hour,Minute,Second;2023/2/916类的实现类的实现实现一个类,就是按照所设定的功能实现一个类,就是按照所设定的功能语义去实现类中的每一个成员函数。语义去实现类中的每一个成员函数。2023/2/917class Clockprivate:int Hour,Minute,Second;public:void SetTime(int h,int m,int s)Hour=h;Minute=m;Second=s;void ShowTime()cout“Current Time:”coutHour“:”Minute“:”Second endl;在类内实现成员函数,编译器按在类内实现成员函数,编译器按内联函数处理内联函数处理在类内实现成员函数,编译器按在类内实现成员函数,编译器按内联函数处理内联函数处理2023/2/918class Clockprivate:int Hour,Minute,Second;public:void SetTime(int h,int m,int s);/给出函数原型给出函数原型 void ShowTime();/给出函数原型给出函数原型;void Clock:SetTime(int h,int m,int s)Hour=h;Minute=m;Second=s;void Clock:ShowTime()cout“Current Time:”coutHour“:”Minute“:”Second 公有成员函数名公有成员函数名(形参列表形参列表);对象的指针对象的指针-公有数据成员公有数据成员2023/2/921举例:一个比较完整的举例:一个比较完整的Clock类类/定义定义Clock类类class Clockprivate:int Hour,Minute,Second;public:void SetTime(int h,int m,int s);void addHour(int h);void addMinute(int m);void addSecond(int s);void ShowTime();2023/2/922/实现实现Clock类中的成员函数类中的成员函数void Clock:SetTime(int h,int m,int s)Hour=h;Minute=m;Second=s;void Clock:addHour(int h)Hour+=h;void Clock:addMinute(int m)Minute+=m;void Clock:addSecond(int s)Second+=s;void Clock:ShowTime()cout“Current Time:”;coutHour“:”Minute“:”Secondendl;2023/2/923/使用使用Clock类类void main()Clock clock_1,clock_2;clock_1.SetTime(9,5,25);clock_2.SetTime(15,16,45);clock_1.addHour(3);clock_2.addMinute(8);clock_1.ShowTime();clock_2.ShowTime();程序输出:程序输出:Current Time:12:5:25 Current Time:15:24:452023/2/924总结:定义和使用类类型的过程总结:定义和使用类类型的过程抽象:抽象:对事物进行抽象对事物进行抽象定义类:定义类:根据抽象的结果定义类的特性根据抽象的结果定义类的特性实现类:实现类:实现类中成员函数的逻辑实现类中成员函数的逻辑使用类:使用类:在程序中定义类的实例,使用在程序中定义类的实例,使用类的公有成员。类的公有成员。2023/2/925在在定定义义类类时时,把把可可以以被被外外部部访访问问的的成成员员说说明明为为public属属性性,作作为为外外部部访访问问类类中中成成员员的的接接口口。把把不不能能被被外外部部访访问问的的成成员员说说明明为为private或或protected属性。属性。私有成员私有成员公有成员公有成员类对外的接口类对外的接口保护成员保护成员2023/2/926请思考以下情况请思考以下情况能调用下面语句吗?能调用下面语句吗?clock_1.Hour=21;如果将如果将ShowTime说明为说明为private属性,属性,还能调用如下语句吗?还能调用如下语句吗?clock_2.ShowTime();2023/2/927练习一练习一设计一个三角形类设计一个三角形类CTriangle,该类满足下,该类满足下述要求:述要求:a)有一个成员函数)有一个成员函数SetEdge,用于设置三,用于设置三角形的边。角形的边。b)有一个成员函数)有一个成员函数GetArea,用于获得三,用于获得三角形的面积。角形的面积。c)有一个成员函数)有一个成员函数GetCircumference,用,用于获得三角形的周长。于获得三角形的周长。在在main函数中,实例化一个函数中,实例化一个Ctriangle类的类的对象,将三条边分别为对象,将三条边分别为3、4、5,然后将,然后将其面积和周长显示在屏幕上。其面积和周长显示在屏幕上。2023/2/928备注:备注:1三角形面积的计算方式如下:三角形面积的计算方式如下:a、b、c分别为三条边,分别为三条边,S代表面积,代表面积,p=(a+b+c)/2,那么,那么S2=p(p-a)(p-b)(p-c)。2求开平方的库函数是求开平方的库函数是sqrt,需要包含,需要包含math.h头文件,使用方式的举例如下:头文件,使用方式的举例如下:int a,b;b=36;a=sqrt(b);那么那么a的值为的值为62023/2/929练习二练习二Need To Do2023/2/930几点说明几点说明在声明类时,具有不同访问属性的成员可以按任在声明类时,具有不同访问属性的成员可以按任意顺序出现。意顺序出现。class Clockprivate:int Hour,Minute,Second;public:void SetTime(int h,int m,int s);void ShowTime();protected:;2023/2/931修饰访问属性关键字可以多次出现。修饰访问属性关键字可以多次出现。class Clockpublic:void SetTime(int h,int m,int s);private:int Hour,Minute,Second;public:void ShowTime();2023/2/932一个成员只能具有一种访问属性,否则会出现歧异一个成员只能具有一种访问属性,否则会出现歧异。class Clockpublic:void SetTime(int h,int m,int s);void ShowTime();private:void ShowTime();int Hour,Minute,Second;2023/2/933例子:简单例子:简单int数组类数组类/数组类的定义数组类的定义const int ARRAY_SIZE=4;class MyArrayint dataARRAY_SIZE;public:int getArraySize();int setVal(int pos,int val);int getMaxVal();int getMinVal();2023/2/934/数组类的实现数组类的实现int MyArray:getArraySize()return ARRAY_SIZE;int MyArray:setVal(int pos,int val)if(posARRAY_SIZE)return-1;datapos=val;return 0;2023/2/935/数组类的实现数组类的实现(续续)int MyArray:getMaxVal()int temp=data0;for(int i=1;itemp)temp=datai;return temp;int MyArray:getMinVal()int temp=data0;for(int i=1;iARRAY_SIZE;i+)if(dataitemp)temp=datai;return temp;2023/2/936/数组类的使用数组类的使用int main()MyArray array;int i,size,v,max,min;size=array.getArraySize();coutplease input size numbers:endl;for(i=0;iv;array.setVal(i,v);max=array.getMaxVal();min=array.getMinVal();coutmax value is:maxendl;coutmin value is:minendl;return 0;2023/2/937改造:为简单改造:为简单int数组类增加公用的私有函数数组类增加公用的私有函数/数组类的定义:增加公用的私有函数数组类的定义:增加公用的私有函数const int ARRAY_SIZE=4;class MyArrayint dataARRAY_SIZE;int getVal(int condition);public:int getArraySize();int setVal(int pos,int val);int getMaxVal();int getMinVal();2023/2/938/数组类的实现:增加和调用公用的私有函数数组类的实现:增加和调用公用的私有函数int MyArray:getVal(int condition)int temp=data0;for(int i=1;itemp)temp=datai;elseif(datai SetTime(9,5,25);p-ShowTime();p-SetTime(10,3,28);p-ShowTime();2023/2/941关键字关键字thisC+为为每每个个非非静静态态成成员员函函数数提提供供一一个个this指针。指针。this指指针针是是一一个个隐隐含含的的指指针针,它它指指向向了了正正在被成员函数操作的那个对象。在被成员函数操作的那个对象。this指指针针不不能能显显式式声声明明,它它只只是是非非静静态态成成员函数的一个形参。员函数的一个形参。2023/2/942this指针举例指针举例class Counterint value;public:void setValue(int value)this-value=value;class Counterint value;public:void setValue(int v)value=v;void main()Counter obj1,obj2;obj1.setValue(1);obj2.setValue(2);2023/2/943class Counterint value;public:void setValue(Counter*this,int v)this-value=v;class Counterint value;public:void setValue(int v)value=v;void main()Counter obj1,obj2;obj1.setValue(1);obj2.setValue(2);编译器做了特殊处理编译器做了特殊处理void main()Counter obj1,obj2;obj1.setValue(&obj1,1);obj2.setValue(&obj2,2);2023/2/944构造函数和析构函数构造函数和析构函数类类的的数数据据成成员员是是不不能能在在定定义义时时直直接接初始化的,以初始化的,以Clock类为例:类为例:class Clockprivate:int Hour=0,Minute=0,Second=0;/错误错误;2023/2/945当当Clock类类被被实实例例化化时时,如如何何初初始始化化对对象象的的状状 态态,即即 如如 何何 初初 始始 化化 Hour、Minute、Second三三个个成成员员呢呢?一一种种可可行行的的方方式式就就是是显式调用初始化函数。显式调用初始化函数。Clock clock1;clock1.SetTime(21,34,43);但是这种方式存在一些不好的情况:但是这种方式存在一些不好的情况:程程序序员员可可能能会会忘忘记记调调用用SetTime()函函数数,导导致对象没有被初始化。致对象没有被初始化。2023/2/946构造函数构造函数实实际际上上,我我们们更更希希望望这这个个初初始始化化工工作作能能够够自自动动进进行行。类类的的构构造造函函数数提提供供了了这种这种自动化功能自动化功能。构造函数是类的一种特殊成员,构造函数是类的一种特殊成员,函数函数名和类名相同,没有名和类名相同,没有返回类型,返回类型,可以可以有参数。当创建类的一个新对象时,有参数。当创建类的一个新对象时,构造函数被构造函数被自动调用自动调用,完成对象的初,完成对象的初始化工作。始化工作。2023/2/947例:为例:为Clock类添加构造函数类添加构造函数class Clockprivate:int Hour,Minute,Second;public:Clock(int h,int m,int s);2023/2/948构造函数初始化数据成员的两种方式构造函数初始化数据成员的两种方式赋值语句的方式:赋值语句的方式:Clock(int h,int m,int s)Hour=h;Minute=m;Second=s;表达式表的方式:表达式表的方式:Clock(int h,int m,int s):Hour(h),Minute(m),Second(s)2023/2/949如果构造函数带有参数,那么在创建对象如果构造函数带有参数,那么在创建对象时必须给出对应的实参。时必须给出对应的实参。如果构造函数仅有一个参数:如果构造函数仅有一个参数:className obj=parameter;如果构造函数有一个或多个参数:如果构造函数有一个或多个参数:className obj(parameter list);如果构造函数有参数,但是在创建对象时如果构造函数有参数,但是在创建对象时又不给出对应的实参,此时编译出错。又不给出对应的实参,此时编译出错。传给构造函数实参的两种方式传给构造函数实参的两种方式2023/2/950void main()Counter counter1(8);Counter counter2=9;Clock clock1(3,5,1);Clock clock2();/错误错误class Counterprivate:int value;public:Counter(int v):value(v);举例举例class Clockprivate:int Hour,Minute,Second;public:Clock(int h,int m,int s);2023/2/951重载构造函数重载构造函数一个类可以提供多个构造函数,但它们的一个类可以提供多个构造函数,但它们的参数表必须不同。重载的目的是为了参数表必须不同。重载的目的是为了满足满足不同的初始化需要不同的初始化需要。class Clockprivate:int Hour,Minute,Second;public:Clock(int h,int m,int s);Clock();Clock(char*timestr);void main()Clock clock1(23,12,0);Clock clock2();Clock clock3(“14:45:32”);2023/2/952具有缺省参数的构造函数具有缺省参数的构造函数构构造造函函数数也也可可以以有有缺缺省省参参数数。如如果果在在类类外外实现该函数时,就不能再说明缺省值了。实现该函数时,就不能再说明缺省值了。class Clockprivate:int Hour,Minute,Second;public:Clock(int h=0,int m=0,int s=0);Clock(const char*timestr);请思考一下,这个类还能再有一个没有任何请思考一下,这个类还能再有一个没有任何请思考一下,这个类还能再有一个没有任何请思考一下,这个类还能再有一个没有任何参数的构造函数吗?即:参数的构造函数吗?即:参数的构造函数吗?即:参数的构造函数吗?即:Clock();Clock();2023/2/953缺省的构造函数缺省的构造函数对对于于没没有有构构造造函函数数的的类类,编编译译器器将将会会自自动动为为它它生生成成一一个个没没有有参参数数的的构构造造函函数数,该函数该函数不做任何工作不做任何工作。class Clockprivate:int Hour,Minute,Second;2023/2/954析构函数析构函数与与构构造造函函数数相相对对的的是是析析构构函函数数。C+通通过过析析构函数来处理对象被销毁时的清理工作。构函数来处理对象被销毁时的清理工作。析析构构函函数数没没有有返返回回类类型型,没没有有参参数数,函函数数名名是在类名前加是在类名前加“”。析析构构函函数数将将会会在在对对象象的的生生存存期期结结束束后后被被自自动动调用调用。如如果果没没有有进进行行显显式式说说明明,系系统统将将会会生生成成一一个个不做任何事的缺省的析构函数。不做任何事的缺省的析构函数。2023/2/955举例:为举例:为Clock类添加析构函数类添加析构函数class Clockprivate:int Hour,Minute,Second;public:Clock(int h=12,int m=0,int s=0);Clock();Clock:Clock()cout“Clock obj destroyed!”endl;2023/2/956void func()Clock obj1,obj2;void main()func();/输出:输出:Clock obj destroyed!Clock obj destroyed!2023/2/957析构函数的典型用法析构函数的典型用法class MyStringprivate:int len;char*buf;public:MyString(int n);void copy(char*src);MyString:MyString(int n)len=n;buf=new charn;void MyString:copy(char*src)strcpy(buf,src);void func()MyString obj(64);obj.copy(“helloworld”);void main()func();!此此时时,obj的的buf所所指指向向的的内存空间没有释放内存空间没有释放2023/2/958class MyStringprivate:int len;char*buf;public:MyString(int n);MyString();void copy(char*src);MyString:MyString(int n)len=n;buf=new charn;void MyString:copy(char*src)strcpy(buf,src);MyString:MyString()delete buf;void func()MyString obj(64);obj.copy(“helloworld”);void main()func();!当当obj对对象象被被释释放放时时,析析构构函函数数被被自自动动调调用用,buf所所指指向的内存空间被释放向的内存空间被释放2023/2/959拷贝构造函数拷贝构造函数构构造造函函数数的的参参数数可可以以是是任任意意类类型型,如如果果将将与与自自己己同同类类的的对对象象的的引引用用作作为为参参数数时时,该构造函数就称为该构造函数就称为拷贝构造函数拷贝构造函数。拷贝构造函数的特点:拷贝构造函数的特点:首首先先,它它是是一一个个构构造造函函数数,当当创创建建对对象象时时系统会自动调用它。系统会自动调用它。其其次次,它它将将一一个个已已经经创创建建好好的的对对象象作作为为拷拷贝贝构构造造函函数数的的参参数数,并并根根据据需需要要将将该该对对象象中的数据成员逐一对应地赋值给新对象。中的数据成员逐一对应地赋值给新对象。2023/2/960示例示例class Pointprivate:float x,y;public:Point(float a,float b)x=a;y=b;Point(Point&obj)x=obj.x;y=obj.y;void main()Point obj1(5,15);/调用调用Point(float,float)Point obj2(obj1);/调用调用Point(A&)Point obj3=obj2;/调用调用Point(A&)2023/2/961缺省的拷贝构造函数的应用缺省的拷贝构造函数的应用如如果果一一个个类类没没有有定定义义拷拷贝贝构构造造函函数数,那那么么C+编编译译器器会会为为该该类类产产生生一一个个缺缺省省的的拷拷贝贝构构造造函函数数。缺缺省省的的拷拷贝贝构构造造函函数数使使用用位位拷拷贝贝的的方方法法来来完完成成对对象象到到对对象象的的复复制制。也也就就是是说说,将将第第一一个个对对象象中中的的数数据据成成员员的的值值原原封封不不动动拷拷贝到第二个对象的数据成员中。贝到第二个对象的数据成员中。a_obja_objb_objb_objBit CopyBit Copy2023/2/962例:缺省的拷贝构造函数的应用例:缺省的拷贝构造函数的应用class Pointprivate:float x,y;public:Point(float a,float b)x=a;y=b;void main()Point obj1(5,15);/调用调用A(float,float)Point obj2(obj1);/调用缺省的拷贝构造函数调用缺省的拷贝构造函数Point obj3=obj2;/调用缺省的拷贝构造函数调用缺省的拷贝构造函数obj2是是obj1的精确拷贝,的精确拷贝,obj3是是obj2的精的精确拷贝确拷贝2023/2/963缺省的拷贝构造函数的缺点缺省的拷贝构造函数的缺点在大多数情况下,缺省拷贝构造函在大多数情况下,缺省拷贝构造函数工作得很好,但在一些特殊的场数工作得很好,但在一些特殊的场合,它的表现将不尽人意。合,它的表现将不尽人意。2023/2/964class MyStringprivate:int len;char*buf;public:MyString(int n);MyString();void copy(char*src);MyString:MyString(int n)len=n;buf=new charn;void MyString:copy(char*src)strcpy(buf,src);MyString:MyString()delete buf;void func()MyString obj1(64);obj1.copy(“helloworld”);MyString obj2=obj1;void main()func();!由由于于调调用用的的是是默默认认的的拷拷贝贝构构造造函函数数,因因此此obj1和和obj2中中的的buf指指向向同同一一内内存存空空间间,当当它它们们被被释释放放时时,该该内内存存空间将被释放两次。空间将被释放两次。2023/2/965改进办法:增加拷贝构造函数改进办法:增加拷贝构造函数class MyStringpublic:MyString(int n);MyString(MyString&obj);MyString:MyString(MyString&obj)len=obj.len;buf=new char len;strcpy(buf,obj.buf);通过自定义拷贝构造函数,可以准确通过自定义拷贝构造函数,可以准确地复制数据,以免发生错误。地复制数据,以免发生错误。2023/2/966拷贝构造函数起作用的地方拷贝构造函数起作用的地方拷拷贝贝构构造造函函数数除除了了在在创创建建新新对对象象时时被调用外,还在以下情况被调用:被调用外,还在以下情况被调用:对象作为函数参数对象作为函数参数函数返回对象函数返回对象2023/2/967举例举例class Counterprivate:int value;public:Counter(int v)value=v;void add(int v)value+=v;void show()coutvalueendl;Counter func(Counter obj)obj.add(6);return obj;void main()Counter b1=5;Counter b2=func(b1);b1.show();b2.show();输出:输出:5 112023/2/968调用调用func(b1)时调用默认的拷贝构造函数时调用默认的拷贝构造函数调用调用return obj时调用默认的拷贝构造函数时调用默认的拷贝构造函数将将func()返返回回值值赋赋给给b2时时调调用用默默认认的的拷拷贝贝构构造函数造函数5b111temp11b25(11)objfunc(b1)return objb2=func(b1)2023/2/969对象数组对象数组与与任任何何其其它它数数据据类类型型一一样样,可可以以创创建建一个类的对象数组。例如:一个类的对象数组。例如:Clock clocks10;通通过过下下标标访访问问数数组组中中的的对对象象,进进而而访访问该对象的公有成员,例如:问该对象的公有成员,例如:clocks3.ShowTime();2023/2/970举例举例class Pointpublic:float x,y;Point()x=0;y=0;Point(float a)x=a;y=0;Point(float a,float b)x=a;y=b;void show()coutx“:”yendl;void main()Point array3;array1.x=5;array1.y=6;array1.show();输出:输出:5:62023/2/971对象数组的初始化对象数组的初始化对对象象数数组组的的初初始始化化过过程程,实实际际上上就就是是调调用用构构造造函函数数对对每每一一个个数数组组元元素素进行初始化的过程。进行初始化的过程。如如果果在在声声明明数数组组时时给给出出每每一一个个数数组组元元素素的的初初始始值值,在在初初始始化化过过程程中中就就会调用会调用最匹配最匹配的构造函数。的构造函数。2023/2/972class Pointpublic:Point()x=0;y=0;Point(float a)x=a;y=0;Point(float a,float b)x=a;y=b;void main()Point array3=Point(3,4),5;举例:对象数组初始化举例:对象数组初始化初始化初始化array0时调用的是时调用的是Point(float,float)构造函数构造函数初始化初始化array1时调用的是时调用的是Point(float)构造函数构造函数初始化初始化array2时调用的是时调用的是Point()构造函数构造函数2023/2/973对象指针的加减操作对象指针的加减操作class Counterprivate:int value;public:Counter(int v)value=v;void show()coutvalueshow();p+;p-show();p+;p-show();输出:输出:5 6 72023/2/974类类型作参数类型的三种方式类类型作参数类型的三种方式对象本身作为参数对象本身作为参数由由于于C+采采用用传传值值的的方方式式传传递递参参数数,因因此此使使用用对对象象本本身身参参数数时时,形形参参是是实实参参的的一一个个拷拷贝贝。在在这这种种情情况况下下,最最好好显显式式地地为为类类定定义义一一个个拷拷贝贝构构造函数,以免出现不容易发现的错误。造函数,以免出现不容易发现的错误。2023/2/975举例举例:对象本身做函数参数对象本身做函数参数class Counterprivate:int value;public:Counter(int v)value=v;void add(int v)value+=v;void show()coutvalueadd(6);输出:输出:5 112023/2/978静态成员静态成员当当用用关关键键字字static说说明明一一个个类类成成员员时时,该成员称为静态成员。因此可以分为:该成员称为静态成员。因此可以分为:静态数据成员静态数据成员静态成员函数静态成员函数2023/2/979静态数据成员静态数据成员class ABCD /声明静态数据成员声明静态数据成员static int s_value;int value;ABCD A,B,C,D;Object AObject AValueValueObject DObject DvaluevalueObject BObject Bvaluevalues_values_valueObject CObject Cvaluevalue类的所有对象共享静态数据成员,因此无论建立多类的所有对象共享静态数据成员,因此无论建立多少个该类的对象,静态数据成员只有一份拷贝。少个该类的对象,静态数据成员只有一份拷贝。静态数据成员属于类,而不属于具体的对象。静态数据成员属于类,而不属于具体的对象。2023/2/980静态数据成员的定义和初始化静态数据成员的