第8讲子对象共用数据的保护_第1页
第8讲子对象共用数据的保护_第2页
第8讲子对象共用数据的保护_第3页
第8讲子对象共用数据的保护_第4页
第8讲子对象共用数据的保护_第5页
已阅读5页,还剩49页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

子对象的初始化、常数据成员、常指针、常引用、常成员函数C++程序设计第8讲子对象、共用数据的保护在程序运行过程中,根据需要可以随时建立或删除的对象;堆对象创建在一些空闲的存储单元中,这些存储单元称为堆。1、堆对象堆内存:C++支持动态数据结构,提供了指针这一特殊形式的数据类型,并在内存中开辟了称为堆的动态存储区。堆是程序共享的空间。栈内存:每个函数都有自己的栈,栈用来在函数之间传递参数。函数中定义的变量保存在栈中,每个C++对象的数据成员也保存在栈中。栈空间不需要显式的分配和释放。复习运算符new、delete复习运算符new、delete(1)new运算符动态创建对象;new<类型说明符>(<初始值列表>)new运算符返回一个与new所分配对象类型相匹配的指针;如果new运算符不能分配到所需要的内存,将返回0,这时为空指针;使用new运算符创建对象时,它可以根据其参数来选择适当的构造函数;在C++中的全局对象和局部对象的生存期是严格定义的,程序员不能以任何方式改变它们的生存期,但是可以创建一些生存期能被程序员控制的对象,它们的分配和释放可以根据程序运行中的操作来决定,可以动态分配和释放对象。new创建数组:(需要给出数组的结构说明)new<类型名>[<算术表达式>]使用new创建对象数组或一般数组时,不能为该数组指定初始值,其初始值为缺省值;例如:A*ptr;ptr=newA[5];使用new[]创建对象数组时,类中必须说明缺省构造函数;功能:删除用new创建的对象或一般类型的指针;delete<指针名>删除对象数组delete[]<指针名>(2)delete运算符例如:冒泡法排序#include<iostream.h>classPaixu{public: Paixu(); Paixu(intn); voidshuru(); voidmaopao(); voiddisp(); ~Paixu();private: intnumb; float*p;};Paixu::Paixu(){numb=0;p=NULL;}Paixu::Paixu(intn){numb=n;p=newfloat[n];}Paixu::~Paixu(){numb=0;delete[]p;}voidPaixu::shuru(){if(numb==0&&p==NULL){cout<<"请输入数组元素的个数:";cin>>numb;p=newfloat[numb];}for(inti=0;i<numb;i++) cin>>p[i];}voidPaixu::maopao(){inti,j;floatt;for(i=0;i<numb-1;i++)for(j=0;j<(numb-1)-i;j++) if(p[j]>p[j+1]) {t=p[j];p[j]=p[j+1];p[j+1]=t;}}voidPaixu::disp(){inti;for(i=0;i<numb;i++) cout<<p[i]<<"";cout<<endl;}intmain(){ Paixushuzu;shuzu.shuru(); shuzu.maopao(); shuzu.disp(); return0;}复习数据类型数据类型

——布尔型数据布尔型变量的说明:

例:boolflag;布尔型数据的取值:

只有false和true两个值bool型数据占据1字节内存。string是一种自定义的类型,可以方便地执行C-串所不能直接执行的一切操作。它处理空间占用问题是自动的,需要多少,用多少。例如:#include<iostream.h>#include<string.h>intmain(){stringstr1(“one”,str2(“tow”);cout<<“交换前的串:\nstr1”<<str1<<“str2”<<str2;str1.swap(str2);cout<<“交换后的串:\nstr1”<<str1<<“str2”<<str2<<endl;Return0;}再强调定义类时的注意事项1、类中的数据成员的类型可以是任意的;包含整型、浮点型、字符型、数组、指针和引用等;2、另一个类的对象(子对象),可以作该类的成员;自身类的对象不可以作该类的成员;一、子对象classN;classM{public:…...private:Nn;M*s;};classN{public:voidf(Mm);……};提前说明类N3、自身类的指针或引用,可以作该类的成员;4、当另一个类的对象作为该类的成员时,如果另一个类的定义在后,需要提前说明;n是N类的对象m是M类的对象classNode{public: Studentstud; //节点数据信息(INFO) stringsName; //节点标示名称 Node*NEXT; //指向下一节点的节点指针(NEXT) Node(stringsName,Node*NEXT=NULL):stud(sName) { this->sName=sName; this->NEXT=NEXT; } Node(stringsName,stringsAddree,stringsPhone,stringsMobile,stringsEmail):stud(sName,sAddree,sPhone,sMobile,sEmail) { //空语句体,用来从文件读数据信息 }};classList //定义一个List类{private: Node* Start; //表头指针,固定在表头 Node* Curr; //当前遍历位置指针 Node* Prev; //当前位置的前节点指针 Node* End; //表尾指针,固定在表尾 int iPosition; //当前节点在表中的位置序号public: List() //构造函数 { Start=Curr=Prev=End=NULL; iPosition=1; }一、子对象子对象即对象成员;当类中出现了子对象(对象成员)时,该类的构造函数要包含对子对象的初始化,通常采用成员初始化列表的方法来初始化子对象;子对象:当一个类的成员是另一个类的对象时,该对象就为子对象;子对象(续)例:分析下列程序的输出结果。#include<iostream.h>classA{public:A(inti,intj){a1=i;a2=j;}voidPrint(){cout<<a1<<","<<a2<<endl;}private:inta1,a2;};classB{private:

Aa;intb;子对象a子对象(续)public:B(inti,intj,intk):a(i,j),b(k){}

voidPrint();};voidB::Print(){

a.Print();cout<<b<<endl;}voidmain(){Bb(6,7,8);b.Print();}对子对象成员函数的调用输出:6,78成员初始化列表a是A类对象,是B类的子对象子对象(续)例:分析下列程序的输出结果。//part.hclassPart{public:Part();Part(inti);~Part();voidPrint();private:

intval;};子对象(续)//part.cpp#include<iostream.h>#include"part.h"Part::Part(){val=0;cout<<"DefaultConstructorofPart."<<endl;}Part::Part(inti){val=i;cout<<"ConstructorofPart"<<val<<endl;}Part::~Part(){子对象(续)

cout<<"DestructorofPart"<<val<<endl;}voidPart::Print(){cout<<val<<endl;}//whole.h#include"part.h"classWhole{public:Whole();子对象(续)

Whole(inti,intj,intk);~Whole();voidPrint();private:

Partone;Parttwo;

intdate;};//whole.cpp#include<iostream.h>#include"whole.h"Whole::Whole(){子对象one、two子对象(续)

date=0;cout<<"DefaultconstructorofWhole."<<endl;}Whole::Whole(inti,intj,intk):two(i),one(j){

date=k;cout<<"ConstructorofWhole."<<endl;}Whole::~Whole(){cout<<"DestructorofWhole."<<endl;}voidWhole::Print(){

one.Print();two.Print();成员初始化列表构造函数体子对象(续)

cout<<date<<endl;}//ex613.cpp#include"whole.h"voidmain(){WholeanObject(5,6,10);anObject.Print();}输出:ConstructorofPart6ConstructorofPart5ConstructorofWhole.6510DestructorofWhole.DestructorofPart5DestructorofPart6子对象(续)

#include"whole.h"voidmain(){WholeanObject;anObject.Print();}输出:DefaultconstructorofPart.DefaultconstructorofPart.DefaultconstructorofWhole.000DestructorofWhole.DestructorofPart0DestructorofPart0子对象(续)子对象必须在成员初始化列表中初始化;说明:建立一个对象时,它的所有子对象一起建立;先执行子对象构造函数,再执行对象的构造函数体;析构函数的执行顺序与构造函数的执行顺序严格相反;构造函数的调用顺序仅与子对象在类中声明的顺序有关,而与成员初始化列表中给出的对构造函数的调用顺序无关;构造函数的成员初始化列表中未给出对子对象的调用,则表示使用子对象的缺省构造函数;二、(9.6)共用数据的保护程序中有些数据是共享的,例如实参与形参,变量与其引用,数据及其指针等。有时在无意之中的误操作会改变有关数据,因此有时需要对数据进行保护,这时可以使用const。回顾一般常量(简单类型的常量)

<类型说明符>const<常量名>或const

<类型说明符><常量名>intconstx=2;或constintx=2;intconsta[3]={1,2,3};

constinta[3]={1,2,3};数组元素的值是常量,不能更新;(一)常对象常对象希望数据成员不被改变的对象,可以声明为常对象<类名>const<对象名>classA{public:A(inti,intj){x=i;y=j;}private:intx,y;};constAa1(3,4);或A

const

a1(3,4);常对象a1注意:常对象中的数据成员为常变量且必须有初值。对象a1中的所有数据成员都不能被修改。可以将对象的成员声明为const,包括常数据成员和常成员函数。常数据成员的作用和用法与一般常变量相似,用关键字const来声明常数据成员。常数据成员的值是不能改变的。1、常数据成员常数据成员只能通过成员初始化列表的方法进行初始化;常数据成员不能被赋值。二、常对象成员注意:

例:分析下列程序的输出结果。#include<iostream>usingnamespacestd;classA{public:A(inti);voidPrint();private:

constinta;staticconstintb;constint&r;

intc;};constintA::b=10;A::A(inti):a(i),r(a){c=8;}私有成员,常引用r私有成员,常量a私有常静态数据成员b成员初始化列表,常成员(除常静态成员外)在此初始化私有常静态数据成员b初始化voidA::Print(){cout<<a<<":"<<b<<":"<<r<<":"<<c<<endl;}intmain(){Aa1(100),a2(0);a1.Print();a2.Print();return0;}输出100:10:100:80:10:02、常成员函数使用const关键字进行说明的成员函数;<类型说明符><函数名>(<参数表>)const;const是函数类型的一个组成部分,在函数实现部分必须带有const关键字;说明:只有常成员函数才能操作常对象;表成员函数与对象之间的操作关系常成员函数(续)例:分析下列程序是否正确。#include<iostream.h>classM{public:M(intx,inty){X=x;Y=y;}

voidMove(intx,inty){X=x;Y=y;}

voidPrint()const{cout<<X<<","<<Y<<endl;}private:intX,Y;};一般成员函数常成员函数常成员函数(续)voidmain(){

constMm1(1,2);m1.Move(3,3);m1.Print();Mm2(3,4);m2.Move(3,3);m2.Print();}常对象m1一般对象m2错误,一般成员函数不能操作常对象正确,常成员函数可以操作常对象常成员函数(续)例:分析下列程序的输出结果。#include<iostream.h>classR{public:R(intr1,intr2){R1=r1;R2=r2;}voidPrint(){cout<<R1<<":"<<R2<<endl;}voidPrint()const{cout<<R1<<";"<<R2<<endl;}private:intR1,R2;};voidmain(){

Ra(5,4);常成员函数(续)

a.Print();

constRb(20,52);b.Print();}输出

5:420;52对重载条件的补充:voidPrint();voidPrint()const;可重载;常对象调用常成员函数,一般对象调用一般成员函数成员函数引用数据成员的操作关系数据成员非const成员函数const成员函数非const数据成员可以使用,也可以改变值可以使用,但不可以改变值const数据成员可以使用,但不可以改变值可以使用,但不可以改变值const对象的数据成员不允许使用和改变值可以使用,但不可以改变值三、常指针和常引用

1、常指针char*constptr1=strptr1;ptr1是一个常量指针;ptr1=strptr2;*ptr1="m";ptr1不可以更新ptr1所指向的变量可以更新;注意const的位置constchar*ptr2=strptr1;ptr2是一个指向字符常量的指针;ptr2=strptr2;*ptr2="m";ptr2可以更新ptr2所指向的字符串不可以更新;错误正确正确错误(1)指向对象的常指针定义指向对象的常指针的形式:类名*const指针变量名=对象地址;例如:Pointt1;Point*constptr1;ptr1=&t1;错,常指针不能被赋值常指针往往作为函数的形参,目的是不允许在函数执行过程中改变指针变量的值,使其始终指向原来的对象。(2)指向常对象的指针变量定义指向常对象的指针变量的形式:const类名*指针变量名;说明:a、如果一个变量已被声明为常量,只能用指向常变量的指针变量指向它,而不能用一般的指针去指向它。例如:constcharc[]=“Boy”,constchar*p1;p1=c;char*p2=c;错,p2不是指向常变量的指针例如:constPointp1(10,12);constPoint*p;p=&p1;Point*p2;p2=&p1;

错b、指向常变量的指针变量除了可以指向常变量外,还可以指向未被声明为const的变量。此时不能通过此指针变量改变该变量的值。例如:charc1=‘a’;constchar*p;p=&c1;*p=‘b’;c1=‘b’;错,不能通过p改变变量c1的值例如:设Point类的数据成员x访问权限是公有的Pointp1(10,12);constPoint*p=&p1;p1.x=18;(*p).x=18;

错c、如果函数的形参是指向非const型变量的指针,实参只能用指向非const变量的指针,而不能用指向const变量的指针,这样,可以在执行函数的过程中可以改变形参指针变量所指向的变量(实参指针变量所指向的变量)的值。如果函数的形参是指向const型变量的指针,在执行函数的过程中不能改变指针变量所指向的变量的值。因此允许实参是指向const变量的指针,或指向非const变量的指针。例如:constcharstr[]=“boy”;voidfun(char*ptr);fun(str);Str是const型数组函数fun的形参是指向非const型变量的指针调用fun函数,实参是const变量的地址,因此错。例如:voidfun(constPoint*p);Pointp1(10,12);fun(&p1);指向常对象的指针最常用于函数的形参,目的是保护形参指针所指的对象,使它在函数执行过程中不被修改。形参实参合法否改变指针所指的变量的值指向非const型变量的指针非const变量的地址合法改变指针所指向的变量的值指向非const型变量的指针const变量的地址非法/指向const型变量的指针const变量的地址合法不可以指向const型变量的指针非const变量的地址合法不可以2、常引用(不能通过引用,更新被引用的对象)const<类型说明符>&<引用名>doublex=1.2;constdouble&v=x;则:v=12.3错误。3、常指针与常引用的作用

使用常参数表明该函数不会更新某个参数所指向或所引用的对象,并使该函数具有更大的适应性;例:分析下列程序的输出结果。#include<iostream.h>constintN=6;voidprint(constint*p,intn);voidmain(){intarray[N];for(inti=0;i<N;i++)cin>>array[i];

print(array,N);}voidprint(constint*p

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论