C++第四章.ppt_第1頁
C++第四章.ppt_第2頁
C++第四章.ppt_第3頁
C++第四章.ppt_第4頁
C++第四章.ppt_第5頁
已閱讀5頁,還剩106頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡(jiǎn)介

1、第4章 建立類和對(duì)象的概念,主要內(nèi)容 4.1 類及其實(shí)例化 4.2 構(gòu)造函數(shù) 4.3 析構(gòu)函數(shù) 4.4 調(diào)用復(fù)制構(gòu)造函數(shù)的綜合實(shí)例 4.5 成員函數(shù)重載及默認(rèn)參數(shù) 4.6 this指針 4.7 一個(gè)類的對(duì)象作為另一個(gè)類的成員 4.8 類和對(duì)象的性質(zhì) 4.9 面向?qū)ο蟮臉?biāo)記圖 4.10 面向?qū)ο缶幊痰奈募?guī)范,4.1.1 定義類 像枚舉和結(jié)構(gòu)一樣,類也是一種用戶自己構(gòu)造的數(shù)據(jù)類型并遵循C+的規(guī)定。 類也要先聲明后使用; 不管聲明的內(nèi)容是否相同,聲明同一個(gè)名字的兩個(gè)類是錯(cuò)誤的,類是具有惟一標(biāo)識(shí)符的實(shí)體; 在類中聲明的任何成員不能使用extern、auto和register關(guān)鍵字進(jìn)行修飾; 類中聲明

2、的變量屬于該類,在某些情況下,變量可以被該類的不同實(shí)例所共享。 類和其他數(shù)據(jù)類型不同的是,組成這種類型的不僅可以有數(shù)據(jù),而且可以有對(duì)數(shù)據(jù)進(jìn)行操作的函數(shù),它們分別叫做類的數(shù)據(jù)成員和類的成員函數(shù),而且不能在類聲明中對(duì)數(shù)據(jù)成員使用表達(dá)式進(jìn)行初始化。,1. 聲明類 類是對(duì)一組性質(zhì)相同對(duì)象的程序描述。在C+中聲明類的一般形式為: class 類名 private: 私有數(shù)據(jù)和函數(shù) public: 公有數(shù)據(jù)和函數(shù) protected: 保護(hù)數(shù)據(jù)和函數(shù) ; 類聲明以關(guān)鍵字class開始,其后跟類名。類所聲明的內(nèi)容用花括號(hào)括起來,右花括號(hào)后的分號(hào)作為類聲明語句的結(jié)束標(biāo)志。這一對(duì)花括號(hào)“ ”之間的內(nèi)容稱為類體。

3、,類中定義的數(shù)據(jù)和函數(shù)稱為這個(gè)類的成員(數(shù)據(jù)成員和成員函數(shù))。 類成員均具有一個(gè)屬性,叫做訪問權(quán)限,通過它前面的關(guān)鍵字來定義。關(guān)鍵字private 、public和protected 以后的成員的訪問權(quán)限分別是私有、公有和保護(hù)的,把這些成員分別叫做私有成員、公有成員和保護(hù)成員。 訪問權(quán)限用于控制對(duì)象的某個(gè)成員在程序中的可訪問性,如果沒有使用關(guān)鍵字,則所有成員默認(rèn)聲明為private權(quán)限。這些關(guān)鍵字的使用順序和次數(shù)也都是任意的。,【例4.1】 描述點(diǎn)的Point類。 class Point /類名Point private: /聲明為私有訪問權(quán)限 int x, y; /私有數(shù)據(jù)成員 public

4、: /聲明為公有訪問權(quán)限 void Setxy(int a, int b); /無返回值的公有成員函數(shù) void Move(int a, int b); /無返回值的公有成員函數(shù) void Display( ); /無返回值的公有成員函數(shù) int Getx( ); /返回值為int的公有成員函數(shù) int Gety( ); /返回值為int的公有成員函數(shù) ; /類聲明以分號(hào)結(jié)束 x和y是私有成員 Setxy、Display、Move、Getx和Gety是公有成員 因?yàn)橹皇锹暶骱瘮?shù),所以可只給出函數(shù)原型。【例4.2】是其等效的聲明方式。,【例4.2】 使用默認(rèn)關(guān)鍵字及改變關(guān)鍵字順序和次數(shù)的Poin

5、t類。 #include using namespace std; class Point /類名Point int x; /默認(rèn)私有數(shù)據(jù)成員 public: /聲明為公有訪問權(quán)限 void Setxy(int, int); /無返回值的公有成員函數(shù)的函數(shù)原型 void Move(int, int); /無返回值的公有成員函數(shù)的函數(shù)原型 void Display( ); /無返回值的公有成員函數(shù)的函數(shù)原型 int Getx( ); /返回值為int的公有成員函數(shù)的函數(shù)原型 int Gety( ); /返回值為int的公有成員函數(shù)的函數(shù)原型 private: /聲明為私有訪問權(quán)限 int y;

6、/私有數(shù)據(jù)成員 ; /類定義以分號(hào)結(jié)束 由此可見,成員函數(shù)聲明的規(guī)則與第3章所述的函數(shù)聲明規(guī)則相同。,2. 定義成員函數(shù) 類中說明的成員函數(shù)用來對(duì)數(shù)據(jù)成員進(jìn)行操作。在類中只對(duì)這些成員函數(shù)進(jìn)行了函數(shù)聲明,還必須在程序中實(shí)現(xiàn)這些成員函數(shù)。 定義成員函數(shù)的一般形式為: 返回類型 類名:成員函數(shù)名(參數(shù)列表) 成員函數(shù)的函數(shù)體 /內(nèi)部實(shí)現(xiàn) 其中“:”是作用域運(yùn)算符,“類名”是成員函數(shù)所屬類的名字,“:”用于表明其后的成員函數(shù)是屬于這個(gè)特定的類?!邦惷?成員函數(shù)名”的意思就是對(duì)屬于“類名”的成員函數(shù)進(jìn)行定義,而“返回類型”則是這個(gè)成員函數(shù)返回值的類型。,定義成員函數(shù)的函數(shù)體。例如Setxy定義如下: v

7、oid Point : Setxy(int a, int b) x=a; y=b; 定義Point的函數(shù)成員Setxy(int a, int b),該成員帶有兩個(gè)整型參數(shù),函數(shù)沒有返回值(void)。 void Point : Move(int a, int b) x=x+a; y=y+b; void Point : Display( ) coutx,yendl; int Point : Getx() return x; int Point : Gety() return y;,可以使用關(guān)鍵字inline將成員函數(shù)定義為內(nèi)聯(lián)函數(shù),例如: inline int Point : Getx() re

8、turn x; 如果在聲明類的同時(shí),在類體內(nèi)給出成員函數(shù)的定義,則默認(rèn)為內(nèi)聯(lián)函數(shù)。例如在類中將聲明Getx的語句“int Getx();”改為“int Getx()return x;”,則Getx為內(nèi)聯(lián)函數(shù)。 一般直接在類體內(nèi)給出簡(jiǎn)單成員函數(shù)的定義。 有些成員函數(shù)的實(shí)現(xiàn)方式不止一種,例如 void Point : Display( ) cout using namespace std;,內(nèi)聯(lián)函數(shù),內(nèi)聯(lián)函數(shù)具有一般函數(shù)的特性,它與一般函數(shù)所不同之處只在于函數(shù)調(diào)用的處理。一般函數(shù)進(jìn)行調(diào)用時(shí),要將程序執(zhí)行權(quán)轉(zhuǎn)到被調(diào)用函數(shù)中,然后再返回到調(diào)用它的函數(shù)中; 而在程序編譯時(shí),對(duì)內(nèi)聯(lián)函數(shù)的任何調(diào)用都被替換成

9、該函數(shù)函數(shù)體內(nèi)的各個(gè)語句,內(nèi)聯(lián)函數(shù)調(diào)用時(shí)不必保存斷點(diǎn)地址等現(xiàn)場(chǎng)環(huán)境,不使用??臻g,沒有函數(shù)調(diào)用的開銷。內(nèi)聯(lián)函數(shù)定義的格式為: inline () 可見它是以目標(biāo)代碼的增加為代價(jià)來換取時(shí)間的節(jié)省。,在使用內(nèi)聯(lián)函數(shù)時(shí),應(yīng)注意如下幾點(diǎn): 在內(nèi)聯(lián)函數(shù)內(nèi)不允許用循環(huán)語句和開關(guān)語句。 如果內(nèi)聯(lián)函數(shù)有這些語句,則編譯將該函數(shù)視同普通函數(shù)那樣產(chǎn)生函數(shù)調(diào)用代碼,遞歸函數(shù)(自己調(diào)用自己的函數(shù))是不能被用來做內(nèi)聯(lián)函數(shù)的。 內(nèi)聯(lián)函數(shù)只適合于只有15行的小函數(shù)。對(duì)一個(gè)含有許多語句的大函數(shù),函數(shù)調(diào)用和返回的開銷相對(duì)來說微不足道,所以也沒有必要用內(nèi)聯(lián)函數(shù)實(shí)現(xiàn)。 內(nèi)聯(lián)函數(shù)的定義必須出現(xiàn)在內(nèi)聯(lián)函數(shù)第一次被調(diào)用之前。 類結(jié)構(gòu)中所

10、有在類說明內(nèi)部定義的函數(shù)是內(nèi)聯(lián)函數(shù)。,3. 數(shù)據(jù)成員的賦值 不能在類體內(nèi)給數(shù)據(jù)成員賦值,即下面的方法是錯(cuò)誤的: Class Point int x=25, y=56; ; 當(dāng)然,在類體外面就更不允許了。 數(shù)據(jù)成員的具體值是用來描述對(duì)象的屬性的。只有產(chǎn)生了一個(gè)具體的對(duì)象,這些數(shù)據(jù)值才有意義,所以又稱對(duì)象的初值或?qū)ο蟪跏蓟?假設(shè)已經(jīng)有了一個(gè)對(duì)象A,則可使用“.”運(yùn)算符調(diào)用成員函數(shù)Setxy賦初值。例如: A.Setxy(25, 56); 將對(duì)象A的數(shù)據(jù)成員x和y分別賦給25和56,即A.x=25, A.y=56。 真正的初始化是使用與Point同名的構(gòu)造函數(shù)Point(int,int)實(shí)現(xiàn)的。產(chǎn)

11、生Point對(duì)象的語句: Point A(25,56);,4.1.2 使用類的對(duì)象及指針 Point類是用戶定義的一種類型,使用Point在程序中聲明變量,具有Point類的類型的變量被稱為Point的對(duì)象。只有產(chǎn)生類的對(duì)象,才能使用這些數(shù)據(jù)和成員函數(shù)。 類Point不僅可以聲明對(duì)象,還可以聲明對(duì)象的引用和對(duì)象的指針,語法與基本數(shù)據(jù)類型一樣。 Point A, B; /定義Point類型的對(duì)象A和B Point *p= /定義R為Point類型對(duì)象B的引用,對(duì)象和引用都使用運(yùn)算符“.”訪問對(duì)象的成員, 指針則使用“-”運(yùn)算符。例如: A.Setxy(25,88); /為對(duì)象A設(shè)置初值 p- D

12、isplay( ) ; /顯示指針p所指對(duì)象A的數(shù)據(jù)成員 /A.x和A.y之值 R.Display( ); /顯示對(duì)象B的數(shù)據(jù)成員B.x和B.y之值,【例4.3】根據(jù)上面對(duì)Point類的定義,演示使用Point類的對(duì)象。 void print(Point a) /使用Point的對(duì)象a作為函數(shù)參數(shù) a.Display(); /顯示對(duì)象a的數(shù)據(jù)成員的值 void main() Point A, B; /聲明對(duì)象 A.Setxy(25,55); /為對(duì)象A賦初值 B=A; /B的數(shù)據(jù)成員取A的數(shù)據(jù)成員之值 A.Display(); /顯示A的數(shù)據(jù)成員 A.Move(-10, 20); /移動(dòng)A p

13、rint(A); /等價(jià)于A.Display(); print(B); /等價(jià)于B.Display() coutA.Getx()endl; /只能使用A.Getx(), /不能使用A.x ,本例中的print函數(shù)使用Point的對(duì)象作為參數(shù)。C+推薦使用下面的引用的形式: void print(Point /錯(cuò)誤!,暫不涉及還沒有介紹的保護(hù)成員,可以歸納出如下規(guī)律: (1) 類的成員函數(shù)可以直接使用自己類的私有成員(數(shù)據(jù)成員和成員函數(shù))。 (2) 類外面的函數(shù)不能直接訪問類的私有成員(數(shù)據(jù)成員和成員函數(shù))。 (3) 類外面的函數(shù)只能通過類的對(duì)象使用該類的公有成員函數(shù),例如print和main函

14、數(shù)。 (4) 類對(duì)象A和B的成員函數(shù)的代碼一樣,不同對(duì)象的區(qū)別是屬性的取值。,在程序運(yùn)行時(shí),通過為對(duì)象分配內(nèi)存來創(chuàng)建對(duì)象。在創(chuàng)建對(duì)象時(shí),使用類作為樣板,故稱對(duì)象為類的實(shí)例。 A和B兩個(gè)對(duì)象占據(jù)內(nèi)存中的不同區(qū)域。A的數(shù)據(jù)是A.x和A.y,而B的數(shù)據(jù)是B.x和B.y,它們各有表現(xiàn)自己的屬性數(shù)據(jù),但用來操作數(shù)據(jù)的代碼均是一樣的,例如A.Getx()和B.Getx()的代碼一樣。 為節(jié)省內(nèi)存,在建立對(duì)象時(shí),只分配用于保存數(shù)據(jù)的內(nèi)存,代碼為每個(gè)對(duì)象共享。類中定義的代碼被放在計(jì)算機(jī)內(nèi)存的一個(gè)公用區(qū)中供該類的所有對(duì)象共享。,表4.1 類Point的兩個(gè)實(shí)例A和B,可以通過類對(duì)象的指針訪問對(duì)象的成員。定義類對(duì)

15、象指針的語法如下: 類名* 對(duì)象指針名; 對(duì)象指針名=對(duì)象的地址; 也可以直接進(jìn)行初始化。例如: 類名* 對(duì)象指針名=對(duì)象的地址; 類對(duì)象的指針可以通過“-”運(yùn)算符訪問對(duì)象的成員,即: 對(duì)象指針名-對(duì)象成員名,【例4.4】演示使用內(nèi)聯(lián)函數(shù)定義Point類及使用Point類指針和引用的完整例子。 #include /包含頭文件 using namespace std; /聲明命名空間 class Point /使用內(nèi)聯(lián)函數(shù)定義類Point private: /聲明為私有訪問權(quán)限 int x, y; /私有數(shù)據(jù)成員 public: /聲明為公有訪問權(quán)限 void Setxy(int a, int

16、b) /無返回值的內(nèi)聯(lián)公有成員函數(shù) x=a; y=b; void Move(int a, int b) /無返回值的內(nèi)聯(lián)公有成員函數(shù) x=x+a; y=y+b; void Display( ) /無返回值的內(nèi)聯(lián)公有成員函數(shù) coutDisplay(); void print(Point,void main() /主函數(shù) Point A, B,*p; /聲明對(duì)象和指針 Point /直接傳遞A的地址作為指針參數(shù) ,程序運(yùn)行結(jié)果如下: 112,115 112,115 -55,78 -55,78 由此可見,使用對(duì)象和對(duì)象指針的效果一樣。,4.1.4 數(shù)據(jù)封裝 面向?qū)ο蟮某绦蛟O(shè)計(jì),是通過為數(shù)據(jù)和代碼建

17、立分塊的內(nèi)存區(qū)域,以便提供對(duì)程序進(jìn)行模塊化的一種程序設(shè)計(jì)方法,這些模塊可以被用做樣板,在需要時(shí)再建立其副本。根據(jù)這個(gè)定義,對(duì)象是計(jì)算機(jī)內(nèi)存中的一塊區(qū)域,通過將內(nèi)存分塊,每個(gè)模塊(即對(duì)象)在功能上保持相對(duì)獨(dú)立。, 這些內(nèi)存塊中不但存儲(chǔ)數(shù)據(jù),而且也存儲(chǔ)代碼,這對(duì)保證對(duì)象是受保護(hù)的這一點(diǎn)很重要。對(duì)象保護(hù)它自己不受未知的外部事件的影響,從而使自己的數(shù)據(jù)和功能不會(huì)因此遭到破壞。 這些內(nèi)存塊的結(jié)構(gòu)可被用做樣板產(chǎn)生對(duì)象的更多副本。例如,一旦定義了一個(gè)窗口對(duì)象,只要內(nèi)存允許,就可以建立許多這樣的對(duì)象。 在面向?qū)ο蟮某绦蛑校瑢?duì)象的行為只有向?qū)ο蟀l(fā)送消息才能引用,例如通過Display發(fā)出顯示消息,所以說面向?qū)ο?/p>

18、是消息處理機(jī)制。面向?qū)ο缶褪菍⑹澜缈闯墒怯梢唤M彼此相關(guān)并能相互通信的實(shí)體即對(duì)象組成的。程序中的對(duì)象映射現(xiàn)實(shí)世界中的對(duì)象。,C+對(duì)其對(duì)象的數(shù)據(jù)成員和成員函數(shù)的訪問是通過訪問控制權(quán)限來限制的。private是限制類之外的函數(shù)的訪問權(quán)。只要將數(shù)據(jù)成員或成員函數(shù)使用private限定,就設(shè)定了一道防線。它還必須留下與外面打交道的接口,這通過具有public權(quán)限的成員函數(shù)實(shí)現(xiàn)。 在C+中,數(shù)據(jù)封裝是通過類來實(shí)現(xiàn)的。在類中指定了各成員的訪問權(quán)限。一般情況下: 將數(shù)據(jù)成員說明為私有的,以便隱藏?cái)?shù)據(jù); 將部分成員函數(shù)說明為公有的,用于提供外界和這個(gè)類的對(duì)象相互作用的接口(界面),從而使得其他函數(shù)(例如main

19、函數(shù))也可以訪問和處理該類的對(duì)象。 對(duì)于那些僅是為支持公有函數(shù)的實(shí)現(xiàn)而不作為對(duì)象界面的成員函數(shù),也將它們說明為私有的。,4.2 構(gòu)造函數(shù),建立一個(gè)對(duì)象時(shí),對(duì)象的狀態(tài)(數(shù)據(jù)成員的取值)是不確定的。為了使對(duì)象的狀態(tài)確定,必須對(duì)其進(jìn)行正確的初始化。C+有一個(gè)稱為構(gòu)造函數(shù)的特殊成員函數(shù),它可自動(dòng)進(jìn)行對(duì)象的初始化。,4.2.1 默認(rèn)構(gòu)造函數(shù) 當(dāng)沒有為一個(gè)類定義任何構(gòu)造函數(shù)的情況下,C+編譯器總要自動(dòng)建立一個(gè)不帶參數(shù)的構(gòu)造函數(shù)。 例如,如果在上面的例子中沒有為Point類定義任何構(gòu)造函數(shù),則 C+編譯器要為它產(chǎn)生一個(gè)默認(rèn)構(gòu)造函數(shù),這個(gè)默認(rèn)構(gòu)造函數(shù)具有下面這種形式: Point:Point( ) 即它的函數(shù)

20、體是空的。因此,當(dāng)建立 Point 類的一個(gè)對(duì)象時(shí),對(duì)象的狀態(tài)是不確定的,即沒有被初始化。,一旦程序定義了自己的構(gòu)造函數(shù),系統(tǒng)就不再提供這個(gè)默認(rèn)構(gòu)造函數(shù)。 如果程序員沒有定義一個(gè)無參數(shù)的構(gòu)造函數(shù),但又聲明了一個(gè)沒有初始化的對(duì)象(如“Point A;”),則因系統(tǒng)已經(jīng)不再提供默認(rèn)構(gòu)造函數(shù),編譯就會(huì)出錯(cuò)。 “默認(rèn)”也稱為“缺省”,本書統(tǒng)一使用“默認(rèn)”。不帶參數(shù)的構(gòu)造函數(shù)又稱作默認(rèn)構(gòu)造函數(shù)。 如果只聲明對(duì)象數(shù)組(即不提供初值),因?yàn)槊總€(gè)元素對(duì)象均需要調(diào)用一次默認(rèn)構(gòu)造函數(shù)來為自己初始化,所以必須要求有一個(gè)默認(rèn)構(gòu)造函數(shù)。,4.2.2 定義構(gòu)造函數(shù) 1. 構(gòu)造函數(shù)的定義和使用方法 構(gòu)造函數(shù)的作用是在對(duì)象被

21、創(chuàng)建時(shí)使用特定的值構(gòu)造對(duì)象,或者說將對(duì)象初始化為一個(gè)特定的狀態(tài)。 在對(duì)象創(chuàng)建時(shí)由系統(tǒng)自動(dòng)調(diào)用。 如果程序中未聲明,則系統(tǒng)自動(dòng)產(chǎn)生出一個(gè)默認(rèn)形式的構(gòu)造函數(shù) 允許為內(nèi)聯(lián)函數(shù)、重載函數(shù)、帶默認(rèn)形參值的函數(shù)。,構(gòu)造函數(shù)的特點(diǎn) 構(gòu)造函數(shù)名與類名相同; 沒有返回值; 定義在public下; 構(gòu)造函數(shù)由系統(tǒng)自動(dòng)調(diào)用; 若不顯式定義,系統(tǒng)自動(dòng)生成一個(gè)不帶參數(shù)的構(gòu)造函數(shù); 顯式定義了構(gòu)造函數(shù)后,默認(rèn)的構(gòu)造函數(shù)不起作用; 構(gòu)造函數(shù)可以重載;,【例4.5】 構(gòu)造函數(shù)的定義和執(zhí)行過程實(shí)例程序。 #include using namespace std; class Point private: int x,y; pu

22、blic: Point( ); /聲明不帶參數(shù)的構(gòu)造函數(shù) Point( int,int ); /聲明帶2個(gè)參數(shù)的構(gòu)造函數(shù) ; Point :Point( ):x(0),y(0) /定義不帶參數(shù)的構(gòu)造函數(shù) cout Initializing default endl; /定義帶2個(gè)參數(shù)的構(gòu)造函數(shù) Point:Point(int a, int b):x(a),y(b) cout Initializing a,b endl;,void main ( ) Point A; /使用不帶參數(shù)的構(gòu)造函數(shù)產(chǎn)生對(duì)象A Point B(15,25); /使用帶參數(shù)的構(gòu)造函數(shù)產(chǎn)生對(duì)象B Point c2; /使用不

23、帶參數(shù)的構(gòu)造函數(shù)產(chǎn)生對(duì)象數(shù)組C Point D2=Point(5,7),Point(8,12); /使用帶參數(shù) /的構(gòu)造函數(shù)產(chǎn)生對(duì)象數(shù)組D ,程序輸出結(jié)果如下: Initializing default Initializing 15,25 Initializing default Initializing default Initializing 5,7 Initializing 8,12 程序中和Point類同名的兩個(gè)成員函數(shù)是構(gòu)造函數(shù):一個(gè)不帶參數(shù),另一個(gè)帶有2個(gè)參數(shù)。,構(gòu)造函數(shù)可以通過構(gòu)造函數(shù)的初始化列表給其數(shù)據(jù)成員賦值 Point:Point(int a, int b):x(a),y

24、(b) 完成“x=a,y=b”的功能,它與下面的方法等價(jià): Point:Point(int a, int b) x=a; y=b; cout Initializing a,b endl; ,構(gòu)造函數(shù)在類體里的聲明形式如下: 類名(形參1, 形參2,形參n); /可以沒有形參 構(gòu)造函數(shù)在類體外定義。可以使用初始化列表或者在構(gòu)造函數(shù)的函數(shù)體內(nèi)定義數(shù)據(jù)成員的初值。假設(shè)數(shù)據(jù)成員為 x1,x2,xn,則有如下兩種形式: 類名:類名(形參1, 形參2,形參n): x1(形參1),x2(形參2),xn(形參n) 類名:類名(形參1, 形參2,形參n) x1=形參1; x2=形參2; xn=形參n; 構(gòu)造函數(shù)

25、的參數(shù)無排列順序,只要保證相互的對(duì)應(yīng)順序即可??墒褂媚J(rèn)參數(shù)或重載。,當(dāng)聲明一個(gè)外部對(duì)象時(shí),外部對(duì)象只是引用在其他地方聲明的對(duì)象,程序并不為外部對(duì)象說明調(diào)用構(gòu)造函數(shù)。如果是全局對(duì)象或靜態(tài)對(duì)象,在 main 函數(shù)執(zhí)行之前要調(diào)用它們的構(gòu)造函數(shù),使用下面的主程序演示全局對(duì)象的情況: 【例4.6】使用前面定義的Point類演示全局對(duì)象的例子。 Point global(5, 7); void main( ) cout Entering main and exiting main“ endl; 程序在進(jìn)入main函數(shù)之前先構(gòu)造全局對(duì)象,輸出“Initializing 5, 7”。進(jìn)入主函數(shù)之后輸出為:

26、Entering main and exiting main。,2. 自動(dòng)調(diào)用構(gòu)造類成員函數(shù) 程序員不能在程序中顯式地調(diào)用構(gòu)造類成員函數(shù),這類函數(shù)是自動(dòng)調(diào)用的。 Point a.Point(x,y); 錯(cuò)誤 Point a(x,y);。正確 編譯系統(tǒng)會(huì)自動(dòng)調(diào)用Point(x,y)產(chǎn)生對(duì)象a并使用x和y將其正確地初始化。 也不能在產(chǎn)生對(duì)象a之后,使用構(gòu)造函數(shù)改變對(duì)象的屬性值。 a.Point(x,y);錯(cuò)誤 如果要改變對(duì)象的屬性值,需要設(shè)計(jì)專門的成員函數(shù),如使用a.Setxy(x,y)改變對(duì)象的屬性值。,4.2.3 構(gòu)造函數(shù)和運(yùn)算符new,運(yùn)算符 new 用于建立生存期可控的對(duì)象并返回這個(gè)對(duì)象的

27、指針。使用 new 建立動(dòng)態(tài)對(duì)象的語法和建立動(dòng)態(tài)變量的情況類似,其不同點(diǎn)是 new 和構(gòu)造函數(shù)一同起作用。 【例4.7】使用前面的Point類演示new運(yùn)算符和構(gòu)造函數(shù)的關(guān)系的例子。 void main( ) Point *ptr1=new Point; Point *ptr2=new Point(5,7); delete ptr1; delete ptr2; 運(yùn)行這個(gè)程序,程序的輸出結(jié)果是: Initializing default Initializing 5,7,當(dāng)使用 new 建立一個(gè)動(dòng)態(tài)對(duì)象時(shí),new 首先分配足以保存Point類的一個(gè)對(duì)象所需要的內(nèi)存,然后自動(dòng)調(diào)用構(gòu)造函數(shù)來初始化這

28、塊內(nèi)存,再返回這個(gè)動(dòng)態(tài)對(duì)象的地址。使用 new 建立的動(dòng)態(tài)對(duì)象在不用時(shí)必須用 delete 刪除,以便釋放所占空間。,4.2.4 構(gòu)造函數(shù)的默認(rèn)參數(shù) 如果程序定義自己的有參數(shù)構(gòu)造函數(shù),又想使用無參數(shù)形式的構(gòu)造函數(shù),解決的方法是將相應(yīng)的構(gòu)造函數(shù)全部使用默認(rèn)參數(shù)設(shè)計(jì)。,【例4.8】 設(shè)計(jì)構(gòu)造函數(shù)的默認(rèn)參數(shù)。 #include using namespace std; class Point private: int x,y; public: Point( int=0,int=0 ); /聲明兩個(gè)參數(shù)均為默認(rèn)參數(shù) ; Point:Point(int a, int b):x(a),y(b) /定義構(gòu)造

29、函數(shù) cout Initializing a,b endl;,void main ( ) Point A; /構(gòu)造函數(shù)產(chǎn)生對(duì)象A Point B(15,25); /構(gòu)造函數(shù)產(chǎn)生對(duì)象B Point c2; /構(gòu)造函數(shù)產(chǎn)生對(duì)象數(shù)組C 聲明構(gòu)造函數(shù)原型時(shí)不需要給出參數(shù)名,即使用“int=0,int=0”。程序輸出如下: Initializing 0,0 Initializing 15,25 Initializing 0,0 Initializing 0,0,4.2.5 復(fù)制構(gòu)造函數(shù),引用在類中一個(gè)很重要的用途是用在復(fù)制構(gòu)造函數(shù)中。這是一類特殊而且重要的函數(shù),通常用于使用已有的對(duì)象來建立一個(gè)新對(duì)象。

30、淺拷貝 就是普通的數(shù)值復(fù)制,沒有為新對(duì)象分配內(nèi)存單元。 在通常情況下,編譯器建立一個(gè)默認(rèn)復(fù)制構(gòu)造函數(shù),這個(gè)復(fù)制構(gòu)造函數(shù)采用淺拷貝來使用已有的對(duì)象來建立新對(duì)象,所以又直譯為拷貝構(gòu)造函數(shù)。,對(duì)類A而言,復(fù)制(拷貝)構(gòu)造函數(shù)的原型為: A:A(A 沒有參數(shù),也沒有返回值,而且不能重載。因此在一個(gè)類中只能有一個(gè)析構(gòu)函數(shù); 當(dāng)撤消對(duì)象時(shí),編譯系統(tǒng)會(huì)自動(dòng)地調(diào)用析構(gòu)函數(shù)。 如果不顯式定義,系統(tǒng)自動(dòng)生成一個(gè)空的析構(gòu) 函數(shù),例如: Point:Point( ) cout Destructor is active endl; 使用下面的測(cè)試程序說明析構(gòu)函數(shù)的作用: void main ( ) Point A(5,

31、68); cout Exiting main endl; 執(zhí)行此程序,其輸出是: Initializing 5,68 /調(diào)用構(gòu)造函數(shù) Exiting main /主程序輸出 Destructor is active/自動(dòng)調(diào)用析構(gòu)函數(shù) 當(dāng)對(duì)象的生存期結(jié)束時(shí),程序?yàn)檫@個(gè)對(duì)象調(diào)用析構(gòu)函數(shù),然后回收這個(gè)對(duì)象占用的內(nèi)存。 全局對(duì)象和靜態(tài)對(duì)象的析構(gòu)函數(shù)在程序運(yùn)行結(jié)束之前調(diào)用。 全局對(duì)象數(shù)組和靜態(tài)對(duì)象數(shù)組的析構(gòu)函數(shù)在程序結(jié)束之前被調(diào)用。 數(shù)組的每個(gè)元素調(diào)用一次析構(gòu)函數(shù)。,4.3.2 析構(gòu)函數(shù)和運(yùn)算符delete 運(yùn)算符 delete 與析構(gòu)函數(shù)一起工作。當(dāng)使用運(yùn)算符 delete 刪除一個(gè)動(dòng)態(tài)對(duì)象時(shí),它首先

32、為這個(gè)動(dòng)態(tài)對(duì)象調(diào)用析構(gòu)函數(shù),然后再釋放這個(gè)動(dòng)態(tài)對(duì)象占用的內(nèi)存,這和使用 new 建立動(dòng)態(tài)對(duì)象的過程正好相反。 【例4.9】使用Point類演示建立和釋放一個(gè)動(dòng)態(tài)對(duì)象數(shù)組的例子。 #include using namespace std; class Point private: int x,y;,public: Point( int=0,int=0 ); /聲明兩個(gè)參數(shù)均為默認(rèn)參數(shù) Point(); /聲明析構(gòu)函數(shù) ; Point:Point(int a, int b):x(a),y(b) /定義構(gòu)造函數(shù) cout Initializing a,b endl; Point:Point( ) /

33、定義析構(gòu)函數(shù) cout Destructor is active endl; void main ( ) Point *ptr = new Point2; delete ptr; ,程序的輸出如下: Initializing 0,0 /調(diào)用構(gòu)造函數(shù) Initializing 0,0 /調(diào)用構(gòu)造函數(shù) Destructor is active/調(diào)用析構(gòu)函數(shù) Destructor is active/調(diào)用析構(gòu)函數(shù) C+使用“ ”號(hào)來說明這是動(dòng)態(tài)對(duì)象數(shù)組 即語句 delete ptr;/注意不要錯(cuò)為ptr ,而且 號(hào)內(nèi)為空 delete 將為動(dòng)態(tài)數(shù)組的每個(gè)對(duì)象調(diào)用一次析構(gòu)函數(shù),然后釋放 ptr 所指向

34、的內(nèi)存。 當(dāng)程序先后創(chuàng)建幾個(gè)對(duì)象時(shí),系統(tǒng)按后建先析構(gòu)的原則析構(gòu)對(duì)象。當(dāng)使用delete調(diào)用析構(gòu)函數(shù)時(shí),則按delete的順序析構(gòu)。,4.3.3 默認(rèn)析構(gòu)函數(shù) 如果在定義類時(shí)沒有定義析構(gòu)函數(shù),C+編譯器要為這個(gè)類產(chǎn)生一個(gè)默認(rèn)的析構(gòu)函數(shù),正如沒有給類定義構(gòu)造函數(shù),C+編譯系統(tǒng)會(huì)產(chǎn)生一個(gè)默認(rèn)構(gòu)造函數(shù)一樣,編譯器也為它產(chǎn)生一個(gè)函數(shù)體為空的默認(rèn)析構(gòu)函數(shù): Test:Test( ) ,4.4 調(diào)用復(fù)制構(gòu)造函數(shù)的綜合實(shí)例,調(diào)用復(fù)制構(gòu)造函數(shù)的情況 (1)當(dāng)用類的一個(gè)對(duì)象去初始化該類的另一個(gè)對(duì)象時(shí),系統(tǒng)自動(dòng)調(diào)用復(fù)制構(gòu)造函數(shù)實(shí)現(xiàn)拷貝賦值。 Point p2(p1); / 用對(duì)象p1初始化對(duì)象p2, 復(fù)制構(gòu)造函數(shù)被

35、調(diào)用(代入法) Point p3=p1; / 用對(duì)象p1初始化對(duì)象p3, 復(fù)制構(gòu)造函數(shù)被調(diào)用(賦值法),(2)當(dāng)函數(shù)的形參是類的對(duì)象,調(diào)用函數(shù),進(jìn)行形參和實(shí)參結(jié)合時(shí)。 void fun1(Point p) coutp.GetX()endl; void main() Point A(1,2); fun1(A); /調(diào)用復(fù)制構(gòu)造函數(shù) (3)當(dāng)函數(shù)的返回值是對(duì)象,函數(shù)執(zhí)行完成,返回調(diào)用者時(shí)。 Point fun2() Point A(1,2); return A; /調(diào)用復(fù)制構(gòu)造函數(shù) void main() Point B; B=fun2(); ,【例4.10】演示調(diào)用構(gòu)造函數(shù)及析構(gòu)函數(shù)的綜合例子。

36、 #include using namespace std; class Point private: int X,Y; public: Point(int a=0, int b=0) /構(gòu)造函數(shù) X=a; Y=b; coutInitializingendl; Point(const Point /復(fù)制構(gòu)造函數(shù),int GetX() return X; int GetY() return Y; void Show()coutX=X,Y=Yendl; Point()coutdelete.X,Yendl; ; Point:Point(const Point ,Point fun() /函數(shù)的返回值

37、為Point類的對(duì)象 Point A(101,202); return A; void main() Point A(42,35); / 對(duì)象A /第1次調(diào)用復(fù)制構(gòu)造函數(shù) Point B(A); / 用A初始化B Point C(58,94); / 對(duì)象C coutcalled display(B)endl; / 第2次調(diào)用復(fù)制構(gòu)造函數(shù) display(B); / 對(duì)象B作為display的實(shí)參,coutNext.endl; coutcalled disp(B)endl; disp(B); coutcall C=fun()endl; /第3次調(diào)用復(fù)制構(gòu)造函數(shù) C=fun(); / fun的返回

38、值賦給對(duì)象C coutcalled disp(C)endl; disp(C); coutout.endl; ,輸出結(jié)果及注釋如下: Initializing /創(chuàng)建對(duì)象A Copy Initializing /調(diào)用復(fù)制構(gòu)造函數(shù),使用對(duì)象A初始化B Initializing /創(chuàng)建對(duì)象C called display(B) /用對(duì)象B作為參數(shù) Copy Initializing /需要調(diào)用復(fù)制構(gòu)造函數(shù) X=42,Y=35 /進(jìn)入函數(shù)體執(zhí)行語句 delete.42,35 /退出函數(shù)時(shí),需要調(diào)用析構(gòu)函數(shù)清除對(duì)象 Next. called disp(B) /使用引用做為參數(shù),則不需要 /調(diào)用復(fù)制構(gòu)造函

39、數(shù) X=42,Y=35 /進(jìn)入函數(shù)體執(zhí)行語句 call C=fun() /C使用函數(shù)fun()的返回值 Initializing /在函數(shù)fun()內(nèi)創(chuàng)建對(duì)象A Copy Initializing /調(diào)用復(fù)制構(gòu)造函數(shù)返回值,delete.101,202 /返回值給對(duì)象C,調(diào)用析構(gòu)函數(shù) /清除臨時(shí)對(duì)象 delete.101,202 /退出函數(shù)體,調(diào)用析構(gòu)函數(shù)清除 /對(duì)象A called disp(C) /使用引用做為參數(shù) X=101,Y=202 /進(jìn)入函數(shù)體執(zhí)行語句 out. delete.101,202 /調(diào)用析構(gòu)函數(shù)清除對(duì)象C delete.42,35 /調(diào)用析構(gòu)函數(shù)清除對(duì)象B delete

40、.42,35 /調(diào)用析構(gòu)函數(shù)清除對(duì)象A,第1句輸出比較簡(jiǎn)單,調(diào)用函數(shù)fun,在其內(nèi)調(diào)用構(gòu)造函數(shù)Point(int,int)創(chuàng)建對(duì)象A。對(duì)象A的生命期與函數(shù)fun同在,結(jié)束調(diào)用時(shí)則調(diào)用析構(gòu)函數(shù)析構(gòu)對(duì)象A。在這個(gè)構(gòu)造與析構(gòu)之間,還有一個(gè)過程發(fā)生,即執(zhí)行“return A;”時(shí),目的是使得C=A,使C的數(shù)據(jù)成員與A的相同,但這要調(diào)用復(fù)制構(gòu)造函數(shù)實(shí)現(xiàn)。復(fù)制構(gòu)造函數(shù)是創(chuàng)建對(duì)象的,它產(chǎn)生一個(gè)臨時(shí)對(duì)象,用這個(gè)臨時(shí)對(duì)象完成C=A,然后再析構(gòu)這個(gè)臨時(shí)對(duì)象,這就是中間兩條輸出信息。這樣,語句“C=func();”就輸出如上4條信息。,4.5 成員函數(shù)重載及默認(rèn)參數(shù) 【例4.11】構(gòu)造一個(gè)求4個(gè)正整數(shù)中最大者的類M

41、ax,并用主程序驗(yàn)證它的功能。 class Max /聲明類 private: /封裝數(shù)據(jù)成員和成員函數(shù) int a,b,c,d; /數(shù)據(jù)成員 int Maxi(int,int); /只允許類內(nèi)部的成員函數(shù)調(diào)用 public: /對(duì)外界的接口 void Set(int,int,int,int); /設(shè)置對(duì)象初值 int Maxi(); /求最大值 A3; /聲明類的對(duì)象數(shù)組,定義結(jié)束,/類中成員函數(shù)的實(shí)現(xiàn) int Max:Maxi(int x,int y) /求二個(gè)數(shù)的最大值 return (xy)?x:y; /使用兩個(gè)默認(rèn)參數(shù) void Max:Set(int x1,int x2,int x

42、3=0,int x4=0) a=x1; b=x2; c=x3; d=x4; int Max:Maxi() /求自己類中四個(gè)數(shù)的最大值 int x=Maxi(a,b);/x和y為Maxi()函數(shù)的局部整數(shù)對(duì)象 int y=Maxi(c,d); return Maxi(x,y); ,/主程序 #include using namespace std; void main() A0.Set(12,45,76,89); /為數(shù)組對(duì)象A0置初值 A1.Set(12,45,76); /為數(shù)組對(duì)象A1置初值 A2.Set(12,45); /為數(shù)組對(duì)象A2置初值 for(int i=0;i3;i+) /輸出對(duì)

43、象求值結(jié)果 coutAi.Maxi() ; ,程序演示了可在聲明類的同時(shí)也聲明類的對(duì)象,這里是聲明對(duì)象數(shù)組A,作用與在主程序里使用“Max A3;”語句相同。為了提高可讀性,一般不在聲明類時(shí)聲明對(duì)象,這里只是為了演示它的性質(zhì)。 程序輸出結(jié)果為:89 76 45 類中重載了函數(shù)Maxi,一個(gè)原型為Maxi(int,int),用來求兩數(shù)中的大者。因?yàn)樗槐蛔约旱某蓡T函數(shù)使用,所以定義為private。 另一個(gè)原型為Maxi(),它調(diào)用兩次Maxi(int,int),然后再用這兩次的結(jié)果作為Maxi(int,int)的參數(shù),求出4個(gè)數(shù)中的最大值。 賦值成員函數(shù)Set使用2個(gè)默認(rèn)參數(shù),是為了書寫方便。

44、,4.6 this指針 在定義Point類的兩個(gè)對(duì)象A和B之后,當(dāng)執(zhí)行語句“A.Setxy(25,55);”時(shí),A.x和A.y就被賦值。但是,函數(shù)Setxy(int,int)作為代碼,在計(jì)算機(jī)里是和具體的對(duì)象分開存儲(chǔ)的。那么,它是怎樣知道,是要對(duì)A進(jìn)行操作而不是對(duì)B進(jìn)行操作呢? 當(dāng)執(zhí)行A.Setxy(25,55 )時(shí),成員函數(shù)Setxy(int,int )有一個(gè)隱藏參數(shù),名為this指針。也就是說,源程序被編譯器編譯后,Setxy(int a, int b )實(shí)際上是如下形式: void Point:Setxy(int a, int b,(Point*)this) this-x =a; thi

45、s-y =b; 成員函數(shù)的this指針指向?qū)ο驛。成員中對(duì)x和y的引用表示是引用對(duì)象A的成員x和y。對(duì)于任何訪問該成員函數(shù)的類的對(duì)象來說,C+編譯器都認(rèn)為是訪問this指針?biāo)赶虻膶?duì)象中的成員。,C+規(guī)定,當(dāng)一個(gè)成員函數(shù)被調(diào)用時(shí),系統(tǒng)自動(dòng)向它傳遞一個(gè)隱含的參數(shù),該參數(shù)是一個(gè)指向接受該函數(shù)調(diào)用的對(duì)象的指針,從而使成員函數(shù)知道該對(duì)哪個(gè)對(duì)象進(jìn)行操作。在程序中,可以使用關(guān)鍵字this來引用該指針。使用this指針,保證了每個(gè)對(duì)象可以擁有自己的數(shù)據(jù)成員,但處理這些數(shù)據(jù)成員的代碼可以被所有的對(duì)象共享。 除非特殊需要,一般情況下都省略符號(hào)“this-”,而讓系統(tǒng)進(jìn)行默認(rèn)設(shè)置。,4.7 一個(gè)類的對(duì)象作為另一個(gè)

46、類的成員 因?yàn)轭惐旧砭褪且环N新的數(shù)據(jù)類型,所以一個(gè)類可以作為另一個(gè)類的成員。 假設(shè)有A和B兩個(gè)類,可以通過在B類里定義A的對(duì)象作為B的數(shù)據(jù)成員,或者定義一個(gè)返回類型為A的函數(shù)作為B的成員函數(shù)。,假設(shè)定義了坐標(biāo)點(diǎn)的類Point,矩形類Rectangle的屬性需要一個(gè)坐標(biāo)點(diǎn)及長(zhǎng)和寬。一個(gè)Point的對(duì)象恰好可以作為矩形的頂點(diǎn)坐標(biāo),即Rectangle可以使用Point的一個(gè)對(duì)象作為數(shù)據(jù)成員。在Rectangle類中,用Point類定義一個(gè)返回Point類型指針的函數(shù)作為Rectangle的成員函數(shù)。 【例4.12】使用對(duì)象成員的例子。 #include using namespace std; c

47、lass Point /定義點(diǎn)類 int x,y; public: void Set(int a,int b)x=a; y=b; int Getx( )return x; int Gety( )return y; ;,class Rectangle /在矩形類里使用Point類的成員 Point Loc; /定義一個(gè)Point類的對(duì)象作為頂點(diǎn) int H,W; / H為高,W為寬 public: void Set( int x, int y, int h, int w); Point* GetLoc( ); /用Point類定義返回指針的函數(shù) int GetHeight( ) return H

48、; int GetWidth( ) return W; ; void Rectangle : Set( int x, int y, int h, int w ) Loc.Set( x, y ); /初始化坐標(biāo)頂點(diǎn) H=h; W=w; Point * Rectangle : GetLoc( ) /返回類型Point*,作 /為Rectangle的成員函數(shù) return /返回對(duì)象Loc的地址,void main( ) Rectangle rect; rect.Set( 10, 2, 25, 20 ); coutGetx( )Gety( )endl; 新類Rectangle具有一個(gè)頂點(diǎn),所以也具有

49、Point類的屬性。這就是類的結(jié)構(gòu)關(guān)系(聚合關(guān)系,有時(shí)又稱包含)。構(gòu)成的新類不能直接操作另一個(gè)類的數(shù)據(jù),必須通過原構(gòu)成類的對(duì)象使用它們的成員函數(shù)來實(shí)現(xiàn),本例使用Loc.Set(x,y)方式實(shí)現(xiàn)。 程序輸出結(jié)果為: 25,20,10,2,4.8 類和對(duì)象的性質(zhì) 4.8.1 類對(duì)象的性質(zhì) 歸納對(duì)象的一些基本特性如下: 對(duì)象之間可以相互賦值。例如,如下語句使A和B的數(shù)據(jù)成員有相同的值: Point A, B;A.Setxy(25,55); B=A; 可使用對(duì)象數(shù)組。例如,“Max A3;”定義數(shù)組A可以存儲(chǔ)3個(gè)Point類的對(duì)象。, 可使用指向?qū)ο蟮闹羔?,使用取地址運(yùn)算符 注意,不能取私有數(shù)據(jù)成員的

50、地址,也不能取成員函數(shù)的地址。 對(duì)象可以用做函數(shù)參數(shù),這時(shí)參數(shù)傳遞可以采用傳值方式,也可以傳址,采用對(duì)象的引用或指針作為參數(shù)。但是,如參數(shù)對(duì)象被修改,相應(yīng)的實(shí)參對(duì)象也將被修改。C+推薦使用引用作為參數(shù)傳遞。為了避免被調(diào)用函數(shù)修改原來對(duì)象的數(shù)據(jù)成員,可以使用const修飾符。, 對(duì)象作為函數(shù)參數(shù)時(shí),可以使用對(duì)象值、對(duì)象引用和對(duì)象地址(指針)。以介紹過的print函數(shù)為例,它們的參數(shù)傳遞形式為: void print(Point a)a.Display; void print(Point 它們的原型分別 print(Point); print(Point / 不完全的類聲明 MembersOnly

51、 *club; / 定義一個(gè)全局變量類指針 void main( ) /函數(shù)體 /主函數(shù) class MembersOnly /類體; / 完全定義該類,第一條語句稱為不完全類聲明,它用于在類沒有完全定義之前就引用該類的情況,可以聲明全局變量指針club。編譯器執(zhí)行到該指針的聲明處時(shí),只了解指針?biāo)割愋褪且粋€(gè)叫MembersOnly的類,而不了解其他任何情況。 不完全聲明的類不能實(shí)例化,企圖實(shí)例化會(huì)產(chǎn)生編譯出錯(cuò)信息; 不完全聲明僅用于類和結(jié)構(gòu),企圖存取沒有完全聲明的類成員,也會(huì)引起編譯出錯(cuò)信息。 另外,將數(shù)據(jù)成員的聲明放在最后,有利于先理解類的界面。,3. 空類 盡管類的目的是封裝代碼和數(shù)據(jù),

52、它也可以不包括任何聲明。例如: class Empty ; 當(dāng)然,這種類沒有任何行為,但可以產(chǎn)生空類對(duì)象。 void main( ) Empty object; 為什么要產(chǎn)生空類呢?在開發(fā)大的項(xiàng)目時(shí),需要在一些類還沒有完全定義或?qū)崿F(xiàn)時(shí)進(jìn)行先期測(cè)試。這常稱為“插頭”,用來保證代碼能正確地被編譯,從而允許測(cè)試其中的一部分。 不過這是早期的做法,對(duì)強(qiáng)類型檢查的編譯器,會(huì)給出一個(gè)警告??山o空類增加一個(gè)無參數(shù)構(gòu)造函數(shù)(見構(gòu)造函數(shù)一節(jié))以消除警告。例如: class Empty public:Empty() ;,4. 類作用域 聲明類時(shí)所使用的一對(duì)花括號(hào)形成所謂的類作用域。在類作用域中聲明的標(biāo)識(shí)符只在類中

53、可見。例如: class example int num; ; int i = num; / 錯(cuò),num在此不可見 int num; / 正確,num與類中說明的數(shù)據(jù) /成員num具有不同的作用域,即使該成員函數(shù)的實(shí)現(xiàn)是在類定義之外給出的,類作用域也包含了類中成員函數(shù)的作用域。 class MyClass int number; public: void set( int ); ; int number; /這個(gè)number不屬于類MyClass void MyClass : set( int i ) number = i; / 使用類MyClass中的標(biāo)識(shí)符number 類中的一個(gè)成員名可以

54、使用類名和作用域運(yùn)算符來顯式指定,這稱為成員名限定。例如: void MyClass : set( int i ) MyClass : number=i; / 顯式指定訪問MyClass /類中的標(biāo)識(shí)符number , 在程序中使用成員選擇運(yùn)算符(“.”或“-”)訪問一個(gè)對(duì)象的成員時(shí),其后的名字是引用該對(duì)象所在類中聲明的成員名。例如: Point A; /聲明類對(duì)象,假設(shè)類 /內(nèi)有成員函數(shù)Getx() int Getx( )return 5; /類外面聲明的函數(shù) int x = Getx( ); /訪問函數(shù)Getx( ), 返回5 int y=A.Getx( ); /訪問類Point中聲明的

55、/成員函數(shù)Getx( ),除非編譯器在處理類聲明時(shí)遇到了標(biāo)識(shí)其結(jié)束的右花括號(hào),否則這個(gè)聲明仍然是引用性聲明。引用性聲明所聲明的類名不能用來建立對(duì)象,只能用來聲明指針或引用,或用在函數(shù)聲明中。例如: class MyClass MyClass member; / 錯(cuò) MyClass *p; / 正確 ; class YourClass private: MyClass d; / 正確 ; 當(dāng)在類MyClass中聲明成員member時(shí),類名MyClass僅作了引用性聲明,因而這個(gè)語句是錯(cuò)誤的。,4.9 面向?qū)ο蟮臉?biāo)記圖 為了設(shè)計(jì)、開發(fā)和相互交流的需要,采用圖像形式將面向?qū)ο蟪绦蛟O(shè)計(jì)對(duì)問題的描述直觀

56、地表示出來。 UML是一種可視化建模語言,主要用于面向?qū)ο蠓治龊徒?。本書主要是借助于它來說明類的有關(guān)知識(shí)。,4.9.1 類和對(duì)象的UML標(biāo)記圖,類和對(duì)象的標(biāo)記符號(hào)類似,它們都只能表示靜態(tài)特征。如圖4.1所示,在UML語言中,類使用短式和長(zhǎng)式兩種方式表示。,短式僅用1個(gè)含有類名的長(zhǎng)方框表示。 長(zhǎng)式使用3個(gè)方框表示。最上面的框中填入類的名稱,中間框中填入屬性(C+中稱為數(shù)據(jù)成員),最下面的框中填入成員函數(shù)(操作)。 屬性和操作可以根據(jù)需要進(jìn)行細(xì)化。,圖4.2 對(duì)象的標(biāo)記圖,對(duì)象的表示有3種方式,最簡(jiǎn)單的是只填寫對(duì)象名稱,完整的方式是給出對(duì)象名和類名(類名在右邊,兩者之間用冒號(hào)連接),并用下劃線將它們標(biāo)注出來。當(dāng)還沒有決定這個(gè)對(duì)象的名稱時(shí),可以不給出對(duì)象名,但不能省去“:”號(hào)。,4.9.2 表示對(duì)象的結(jié)構(gòu)與連接 只有定義和描述了對(duì)象類之間的關(guān)系,各個(gè)對(duì)象類才能構(gòu)成一個(gè)整體的、有機(jī)的系統(tǒng)模型,這就是對(duì)象類的結(jié)構(gòu)與連結(jié)關(guān)系。 對(duì)象結(jié)構(gòu)是指對(duì)象之間的分類(繼承)關(guān)系和組成(聚合

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。

評(píng)論

0/150

提交評(píng)論