零點(diǎn)起飛學(xué)C++之命名空間和作用域_第1頁(yè)
零點(diǎn)起飛學(xué)C++之命名空間和作用域_第2頁(yè)
零點(diǎn)起飛學(xué)C++之命名空間和作用域_第3頁(yè)
零點(diǎn)起飛學(xué)C++之命名空間和作用域_第4頁(yè)
零點(diǎn)起飛學(xué)C++之命名空間和作用域_第5頁(yè)
已閱讀5頁(yè),還剩22頁(yè)未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

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

文檔簡(jiǎn)介

1、第14章 命名空間和作用域命名空間(namespace)是一種將相關(guān)的類型進(jìn)行分組的邏輯命名方案。它將各種命名實(shí)體進(jìn)行分組,各組間可以互不影響,避免出現(xiàn)重名,這與Java的包機(jī)制類似。學(xué)習(xí)本章,讀者可以更好理解大型開發(fā)中的各種設(shè)計(jì)規(guī)劃,更好地深入學(xué)習(xí)項(xiàng)目構(gòu)建。14.1 為什么使用命名空間程序員在給對(duì)象命名時(shí),一般都會(huì)使用一些有意義的記號(hào),這些記號(hào)包括單詞、漢語(yǔ)拼音,或者縮寫等。所以很可能出現(xiàn)多個(gè)實(shí)體擁有不同的功能卻有相同的名稱。但是,C+中采用的是單一的全局變量命名空間,在這單一的空間中,實(shí)體必須有唯一的名字。但現(xiàn)實(shí)中經(jīng)常會(huì)出現(xiàn)同名現(xiàn)象,這種命名沖突被稱為名字污染。當(dāng)然,為了解決這一問題,程序

2、員可以盡量給自己的實(shí)體命名一個(gè)特有的名字。比如myString、stringOfTom等。甚至可以在實(shí)體名稱上加上一個(gè)隨機(jī)的編碼,如string6547、string82734798等。但是這樣做不僅意義不明確,而且無論在使用時(shí)還是修改時(shí)都很不方便。更為糟糕的是,有時(shí)程序員不得不將實(shí)體命名為一個(gè)簡(jiǎn)單而容易沖突的名字,如user_name、password、login等。為了從根本上解決名字污染問題,C+引入了命名空間的命名機(jī)制,它提供了一種組織相關(guān)實(shí)體的邏輯方式??梢詫⒚臻g理解為一個(gè)文件夾,其內(nèi)的對(duì)象就像一個(gè)個(gè)文件,不同文件夾內(nèi)的文件可以重名。在使用重名的文件時(shí),只需要說明是哪個(gè)文件夾下的

3、就行了。但它與文件夾又有本質(zhì)上的區(qū)別,命名空間是一種邏輯組合,而不是文件夾那樣的物理組合。命名空間為實(shí)體提供了上下文環(huán)境。一個(gè)實(shí)體可在多個(gè)命名空間中定義,它在不同命名空間中的命名是互不相干的。這樣,在一個(gè)新的命名空間中可定義任何實(shí)體,它們不會(huì)與任何已有的實(shí)體發(fā)生沖突,因?yàn)橐延械亩x都處于其他命名空間中。例如Tom是X公司的員工,另一個(gè)Tom是Y公司的員工。由于它們?cè)诓煌墓荆跃哂邢嗤拿植⒉粫?huì)帶來麻煩,因?yàn)楣揪拖喈?dāng)于一個(gè)獨(dú)立的名字空間。如果兩人在同一家公司,那將肯定會(huì)引起許多不必要的麻煩。14.2 定義命名空間命名空間用namespace來聲明,后跟空間的名稱,名稱之后是由花括號(hào) 包

4、含起來的聲明塊。在一個(gè)名字空間內(nèi)聲明的實(shí)體被稱為名字空間成員(namespace member),每個(gè)成員都必須指向該名字空間內(nèi)的唯一實(shí)體,不同的名字空間可以具有相同名字的成員。命名空間的格式如下所示。namsespace space_name.其中,namespace是名字空間的關(guān)鍵字,space_name是空間的名稱,花括號(hào)內(nèi)是命名的實(shí)體。實(shí)體可以是變量(可以帶有初始化)、常量、結(jié)構(gòu)體、類等各種類型,也可以是另一個(gè)命名空間。把一個(gè)實(shí)體放在名字空間中并不會(huì)改變其意義,唯一的不同是這樣的聲明所引入的名字要與名字空間名復(fù)合起來。程序員可以根據(jù)需要設(shè)置多個(gè)命名空間,每個(gè)命名空間名代表一個(gè)不同的命名

5、空間域,但是不同的命名空間不能同名?!臼纠?4-1】 兩個(gè)名字空間。分析:該示例定義了兩個(gè)命名空間SpaceA和SpaceB,在兩個(gè)空間內(nèi)都有同樣的類名A和變量str,但是在使用時(shí)并沒有引入沖突。注意:名字空間的說明與類的聲明有點(diǎn)兒像,但是它不能以“;”結(jié)束。名字空間的定義可以是不連續(xù)的??梢詫⒁粋€(gè)名字空間拆成多個(gè)部分或跨越多個(gè)文件,但卻具有同一個(gè)名字。這時(shí)它們都將屬于同一個(gè)名字空間,既名字空間的定義是可累積的。例如,如果在上例中還有如下語(yǔ)句,變量hello將和類A和串str同屬空間SpaceA。namespace SpaceAchar *hello=hello world;還可以將上述語(yǔ)句放

6、在另一個(gè)文件內(nèi),使用時(shí)將該文件引入,這樣字符串hello仍然和示例中的命名空間SpaceA是同一個(gè)空間。名字空間還可以嵌套,既在名字空間內(nèi)還可以有另一個(gè)名字空間。例如,在示例14-1的名字空間SpaceA內(nèi)還可以定義另一個(gè)名字空間SpaceAA。【示例14-2】 在示例14-1中嵌入另一個(gè)空間的定義。分析:空間SpaceAA被空間SpaceA嵌套在內(nèi)部,它的成員聲明被隱藏在該嵌套域中。這樣的成員會(huì)被自動(dòng)地加上最外層名字空間名,形成多空間前綴。所以,如果使用它就需要寫成:SpaceA:SpaceAA:str;此外,名字空間中的名字部分也可以省略,這時(shí)就定義了一個(gè)未命名的名字空間。例如,將示例中n

7、amespace SpaceB的名稱SpaceB去掉,就定義了一個(gè)未命名的名字空間。未命名空間的實(shí)體將只在定義它的文件內(nèi)有效。不像其他的名字空間,未命名的名字空間的定義局部于定義它的文件內(nèi),而不能跨越多個(gè)文本文件。14.3 如何使用命名空間使用命名空間有兩種方法:域限定符和使用using聲明。下面將分別介紹它們的用法和別名的用法。1使用域限定符域限定符是:,其使用方法如下所示。space_name:space_member;如果命名空間是嵌套的,則要連續(xù)寫出所有空間名。space_name1:space_name2:.:space_nameN:space_member;但是,如果實(shí)體在未命名的

8、空間內(nèi),則可以直接訪問,就像一個(gè)全局變量一樣。2使用using聲明命名空間一個(gè)using聲明一次只能作用于一個(gè)命名空間,它明確指出了用到的命名空間。其格式如下:using namespace name_space;using name_space:space_memeber;第一種方式表示將命名空間引入到該文件中,以后對(duì)該命名空間內(nèi)的成員訪問時(shí),就不需要加完整的空間限定了。第二種方式表示只引入space_member這一個(gè)成員,而其他成員不可見。3別名有時(shí)名字空間的命名太長(zhǎng)不方便使用,這時(shí)可以給它定義一個(gè)別名。namespace othername=space_name;當(dāng)使用space_na

9、me時(shí),就可以用名字othername來替代。假設(shè)有命名空間MyFirstNameSpace,在不引起歧義和沖突的情況下,可以給它一個(gè)別名My。【示例14-3】 給名字空間MyFirstNameSpace定義另一個(gè)別名。namespace My=MyFirstNameSpace;分析:以后就可以使用My,就像直接使用MyFirstNameSpace一樣?!臼纠?4-4】 演示一個(gè)名字空間的完整使用示例,文件otherfile.h定義一個(gè)名字空間OtherFile。文件test14_4.cpp中的代碼使用了otherfile.h中定義的名字空間。分析:該示例定義了3個(gè)名字空間OtherFile和

10、ThisFile,以及1個(gè)未命名的空間。使用OtherFile時(shí),需要將它所在的文件包含進(jìn)來,而且使用了using將該名字空間進(jìn)行了聲明。所以,如果不加限定,則變量str和函數(shù)fun都將是命名空間OtherFile的成員。而要使用ThisFile的成員就必須加限定域。unnamed在未命名空間內(nèi),所以可以直接訪問。技巧:使用未命名的名字空間可以取代static限定,將實(shí)體的作用域限定在一個(gè)文件內(nèi)部。14.4 我的地盤我做主作用域作用域就是實(shí)體的作用范圍,它限定了某個(gè)實(shí)體的生存期和有效期。作用域是編程中經(jīng)常要考慮的問題,也是經(jīng)常會(huì)出現(xiàn)問題的地方。本節(jié)將詳細(xì)講解C+中的各種作用域的概念和注意事項(xiàng)。

11、14.4.1 什么叫作用域程序中的實(shí)體名字并不總是有效或可用的,它有效或可用的代碼范圍就是它的作用域。作用域的使用提高了程序邏輯的局部性,增強(qiáng)了程序的可靠性,減少了名字沖突。在C+中作用域可以從5個(gè)層面來理解。文件作用域:也稱做全局作用域,它限定實(shí)體的作用范圍僅在某個(gè)文件內(nèi);命名空間:它限定實(shí)體的作用范圍僅在某個(gè)命名空間內(nèi),命名空間可以跨越多個(gè)文件;類作用域:它限定實(shí)體的作用范圍僅在該類內(nèi)有效;函數(shù)作用域:它限定實(shí)體僅在聲明它的函數(shù)內(nèi)有效;塊作用域:也叫局部作用域,它限定實(shí)體僅在一個(gè)花括號(hào)內(nèi)有效。14.4.2 作用域的分類對(duì)應(yīng)于14.4.2節(jié),作用域可以從5個(gè)層面來劃分,分別是文件作用域、命名

12、空間、類作用域、函數(shù)作用域以及塊作用域等。1文件作用域文件作用域是全局的,它在所有其他作用域之外說明。其作用域從定義處開始,一直延伸到源文件結(jié)束。如果某個(gè)文件被引入到另一個(gè)文件中,則原文件中的作用域也擴(kuò)展到該文件中,直到該文件結(jié)束。但是如果用static來修飾實(shí)體,該實(shí)體將僅在定義它的文件內(nèi)有效。用戶也可以用匿名名字空間來代替static修飾符。每個(gè)文件都有一個(gè)匿名名字空間,不同文件的匿名空間互不影響。2命名空間命名空間的引入目的是為了解決名字沖突的問題。如果不使用命名空間,就必須給全局變量和函數(shù)賦予特定名字,以防止名字沖突。使用名字空間,就可以使用名字空間的限定來避免名字沖突的問題。當(dāng)然更主

13、要的是可以通過名字空間別名,使用聲明(特定的名字)和使用指示(全部名字)來達(dá)到既能有效防止沖突,又能在已確定的上下文中更方便地訪問名字的作用。3類作用域當(dāng)用struct和class定義一個(gè)自定義類型時(shí),就定義了一個(gè)類作用域。它指在類的定義中由一對(duì)花括號(hào)所包含起來的部分。處于類作用域下的變量和函數(shù)通常被稱為成員變量和成員函數(shù),它們可以是靜態(tài)的(屬于類型),也可以是非靜態(tài)的(屬于實(shí)例)。靜態(tài)的成員變量和成員函數(shù)與非成員變量和函數(shù)類似,而類型在這里只是起到一個(gè)特殊的名字空間的作用,公共的靜態(tài)成員函數(shù)如果是可見的,那也是可訪問的,也就具備外部鏈接的能力。在類的定義中可知,類域中可以定義變量,也可以定義

14、函數(shù)。從這一點(diǎn)上看類域與文件域很相似。但是,類域又不同于文件域。在類域中定義的變量不能使用auto、register和extern等修飾符,只能用static修飾符,而定義的函數(shù)也不能用extern修飾符。另外,在類域中的靜態(tài)成員和成員函數(shù)還具有外部的連接屬性。4函數(shù)作用域每個(gè)函數(shù)都構(gòu)成了一個(gè)函數(shù)域,函數(shù)域的概念跟變量的存儲(chǔ)位置和生命期有關(guān)。函數(shù)的參數(shù)和在函數(shù)中聲明并定義的變量被稱為局部變量或者是自動(dòng)變量。它們分配在堆棧上。它們隨著函數(shù)的執(zhí)行而生成,隨著函數(shù)的退出而消亡。而靜態(tài)成員變量和非成員變量則分配在靜態(tài)存儲(chǔ)區(qū)中,它們的位置是固定的,生命期從程序啟動(dòng)一直到程序關(guān)閉。5塊作用域局部域的作用通

15、常是用來進(jìn)一步限制局部變量的使用范圍。在某個(gè)局部域聲明的局部變量,在退出該局部域時(shí)會(huì)被自動(dòng)銷毀。用戶自己產(chǎn)生的代碼塊(局部域)多用于所謂的關(guān)鍵區(qū),用來同步線程對(duì)外部狀態(tài)的訪問。如果函數(shù)需要寫的很長(zhǎng),刻意地區(qū)分不同的局部域也有助于代碼的可讀性和防止不必要的錯(cuò)誤。技巧:當(dāng)局部變量和全局變量同名時(shí),所有對(duì)變量名的引用都會(huì)指向局部變量。此時(shí),如果使用全局變量,就要用作用域解析符:來限定變量?!臼纠?4-5】 作用域的使用舉例,文件other.h中定義一個(gè)函數(shù)fun()。主文件test14_5.cpp中使用other.h中定義的函數(shù)fun()。分析:該示例中,定義了命名空間mySpace、類myClass,它們的成員分別局限在命名空間和類內(nèi)。函數(shù)fun1()和字符串str1是文件內(nèi)全局有效。頭文件other.h引入了另外兩個(gè)實(shí)體fun和str,它們的作用域自動(dòng)擴(kuò)展到了主文件內(nèi),變成全局有效。所以,如果fun1和str1寫成fun和str,則將會(huì)和other.h文件中的f

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫(kù)網(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)論