版權說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權,請進行舉報或認領
文檔簡介
內(nèi)容提要函數(shù)的定義函數(shù)的調(diào)用函數(shù)的嵌套調(diào)用函數(shù)的遞歸調(diào)用局部變量和全局變量全局函數(shù)和靜態(tài)函數(shù)
第6章
函數(shù)1內(nèi)容提要內(nèi)聯(lián)函數(shù)函數(shù)重載默認參數(shù)的函數(shù)函數(shù)指針函數(shù)與數(shù)組、指針及引用等的關系命名空間
第6章
函數(shù)2Ch6函數(shù)
一個C++程序是由若干個源程序文件構成的,而一個源程序文件是由若干個函數(shù)構成。//Demo:源程序文件1.cpp+源程序文件2.cpp
3Ch6函數(shù)
從用戶的角度看,有兩種不同的函數(shù):庫函數(shù)和用戶自定義函數(shù)。所謂庫函數(shù)也稱標準函數(shù),由C++系統(tǒng)提供。而用戶自定義函數(shù)則需要用戶先定義,后使用。46.1函數(shù)的定義
6.1函數(shù)的定義6.1.1函數(shù)的定義格式定義函數(shù)的一般形式:函數(shù)返回值的數(shù)據(jù)類型標識符
函數(shù)名(形式參數(shù)表及其類型)
{函數(shù)體}56.1函數(shù)的定義
如:voiddisplay_larger(intx,inty){if(x<y)cout<<"Thelargeris:"<<y<<"\n";else
if(x>y)cout<<"Thelargeris:"<<x<<"\n";else
cout<<"Twovaluesareequal."<<"\n";}66.1函數(shù)的定義
在C++中定義函數(shù)時注意:(1)函數(shù)的形參及類型說明要采用新的ANSI標準,即必須放在函數(shù)名后面的括號內(nèi)。(2)當形參有多個時,必須用逗號隔開。(3)如果函數(shù)是無參函數(shù),括號也不能省略(括號內(nèi)最好寫上void)。(4)所有的函數(shù)都要先定義,后使用(調(diào)用)。(5)不能省略函數(shù)值的類型,必須表明該函數(shù)的函數(shù)值的類型,即使該函數(shù)沒有返回值,也要注明函數(shù)值的類型為void。76.1函數(shù)的定義
6.1.2
函數(shù)的參數(shù)和函數(shù)的返回值所謂調(diào)用函數(shù)是指在程序中使用了該函數(shù)。
--主調(diào)函數(shù)(調(diào)用其他函數(shù)的函數(shù))
--被調(diào)函數(shù)(被主調(diào)函數(shù)調(diào)用的函數(shù))
--調(diào)用點(主調(diào)函數(shù)調(diào)用被調(diào)函數(shù)的地方)1.形式參數(shù)和實際參數(shù)(形參和實參)在調(diào)用函數(shù)時,大多數(shù)情況下,主調(diào)函數(shù)和被調(diào)函數(shù)之間有數(shù)據(jù)傳遞關系。而函數(shù)之間的數(shù)據(jù)傳遞就是靠函數(shù)的參數(shù)進行的,而對無參函數(shù)的調(diào)用,沒有數(shù)據(jù)傳遞。86.1函數(shù)的定義
在定義函數(shù)時,函數(shù)名后面括號內(nèi)的變量名為“形式參數(shù)”(形參)。在調(diào)用函數(shù)時,函數(shù)名后面括號內(nèi)的表達式為“實際參數(shù)”(實參)。例
voidmain(void){
int
a,b,c;
cin>>x>>y;
c=max(a,b);
cout<<“maxis”<<c;
}
int
max(int
x,inty){
intz;z=x>y?x:y;return(z);
}96.1函數(shù)的定義
關于形參和實參說明幾點:(1)實參可以是變量、常量、或表達式,但必須有確定的值。而形參必須是變量。(2)形參變量,只有存在發(fā)生函數(shù)調(diào)用時,形參才被分配存儲單元,在調(diào)用結束時,形參所占的內(nèi)存單元被釋放。(3)實參與形參的類型必須一致,否則會發(fā)生“類型不匹配”的錯誤。(4)實參對形參的數(shù)據(jù)傳遞是“值傳遞”,即單向傳遞。由實參把數(shù)據(jù)傳給形參,并且存儲單元與形參是不同的單元,并將實參對應的值依次傳遞給形參變量。調(diào)用結束后,形參單元被釋放,而實參單元保留并維持原值。106.1函數(shù)的定義
Demos:p163例--ch8_12.cpp值參數(shù)傳遞方式.cpp
參數(shù)傳遞方式.cpp
指針類型的值參數(shù).cpp116.1函數(shù)的定義
2.函數(shù)的返回值(1)函數(shù)的返回值是通過函數(shù)中的return語句獲得的,return語句的格式為:return(表達式);或return表達式;return語句的功能有兩個,
(A)強制程序執(zhí)行的流程從被調(diào)函數(shù)返回到主調(diào)函數(shù);
(B)給主調(diào)函數(shù)帶回一個確定的函數(shù)值。126.1函數(shù)的定義
如:
intmax(inta,intb){return(a>b?a:b);}136.1函數(shù)的定義
(2)函數(shù)值的類型:函數(shù)返回值的類型就是在定義函數(shù)時的函數(shù)值的類型。在定義函數(shù)時,函數(shù)值說明的類型和return語句中的表達式類型不一致時,則以函數(shù)類型為準。(3)如果被調(diào)用函數(shù)中沒有return語句,為了明確表示函數(shù)“不返回值”,要用void定義無類型。如:voidprint(void){
cout<<“Clanguage\n”);}這樣系統(tǒng)就保證不使函數(shù)帶回任何值。//Demo:函數(shù)的定義和使用例.cpp
螺旋隊列.cpp14內(nèi)容提要函數(shù)的定義函數(shù)的調(diào)用函數(shù)的嵌套調(diào)用函數(shù)的遞歸調(diào)用局部變量和全局變量全局函數(shù)和靜態(tài)函數(shù)
第6章
函數(shù)156.2函數(shù)的調(diào)用
6.2函數(shù)的調(diào)用1.函數(shù)調(diào)用的格式
函數(shù)名(實參數(shù))
說明:(1)如果調(diào)用的是無參函數(shù),則實參表可略去,但函數(shù)的括號不能省。
(2)如果實參表中有多個參數(shù),之間用逗號隔開,實參的類型、個數(shù)應與形參順序一一對應。
166.2函數(shù)的調(diào)用
函數(shù)通過下列三種方式完成函數(shù)調(diào)用:(1)函數(shù)調(diào)用語句:即以一個函數(shù)的調(diào)用后面加上“;”作為一個語句。如:fun(5);(2)函數(shù)表達式:即函數(shù)出現(xiàn)在一個表達式中,這時要求函數(shù)帶回一個確定的值以參加表達式的運算。如:c=2*max(a,b);(3)函數(shù)參數(shù):以函數(shù)的調(diào)用作為一個函數(shù)的實參。如:M=max(a,max(b,c));176.2函數(shù)的調(diào)用
2.調(diào)用函數(shù)時的前提條件在一個函數(shù)中調(diào)用另一個函數(shù),需要具備的條件:(1)首先被調(diào)用的函數(shù)必須已經(jīng)存在的函數(shù)。如果調(diào)用庫函數(shù),一般還應在本文件的開頭用#include命令將調(diào)用有關庫函數(shù)時所需用到的信息包含到本文件來。(2)如果調(diào)用用戶自己定義的函數(shù),則必須對被調(diào)函數(shù)的原型進行說明(否則必須函數(shù)先定義,后才能被調(diào)用),函數(shù)的原型包括:
函數(shù)值的類型標識符被調(diào)用函數(shù)名(形參及其類型表);
(3)對函數(shù)原型的說明,通常放在程序的頂部,也可以存放到一個頭文件中,然后利用#include語句嵌入到程序中。//Demo:
mymain.cpp+myheaderfile.h186.2函數(shù)的調(diào)用
3.函數(shù)的定義與函數(shù)原型說明之間的區(qū)別(1)函數(shù)的“定義”是一個函數(shù)功能的確立,包括指定函數(shù)名,函數(shù)返回值的類型,形參及其類型,函數(shù)體等,它是一個完整的、獨立的函數(shù)單位。(2)函數(shù)的原型說明則只是對將要使用的函數(shù)進行“框架”說明,它包括函數(shù)類型、函數(shù)名、一對括號及其括號內(nèi)的各個函數(shù)形參的類型。形參名可以省略。(3)對函數(shù)進行原型說明的作用是告訴系統(tǒng),在本程序中將要用到的函數(shù)是什么樣的“結構模型”,以便確保在主調(diào)函數(shù)中必須按此“模型”對函數(shù)進行調(diào)用(即要匹配)。19內(nèi)容提要函數(shù)的定義函數(shù)的調(diào)用函數(shù)的嵌套調(diào)用函數(shù)的遞歸調(diào)用局部變量和全局變量全局函數(shù)和靜態(tài)函數(shù)
第6章
函數(shù)206.3函數(shù)的嵌套調(diào)用
6.3函數(shù)的嵌套調(diào)用
C++語言中函數(shù)的定義是平行的、獨立的,所以,函數(shù)的定義是不能嵌套進行的,但函數(shù)的調(diào)用可以。嵌套調(diào)用即在調(diào)用一個函數(shù)的過程中,又調(diào)用另一函數(shù)。216.3函數(shù)的嵌套調(diào)用
main()函數(shù){
……
調(diào)用a函數(shù)
……}
a()函數(shù)
{……
調(diào)用b函數(shù)
……}
b()函數(shù)
{…………}
226.3函數(shù)的嵌套調(diào)用
在本例中,main函數(shù)在執(zhí)行過程中,調(diào)用了函數(shù)a,而函數(shù)a中又調(diào)用了函數(shù)b,所以,這就是一種嵌套調(diào)用。要注意:在函數(shù)嵌套調(diào)調(diào)用過程中程序執(zhí)行的流程和返回點的問題。23內(nèi)容提要函數(shù)的定義函數(shù)的調(diào)用函數(shù)的嵌套調(diào)用函數(shù)的遞歸調(diào)用局部變量和全局變量全局函數(shù)和靜態(tài)函數(shù)
第6章
函數(shù)246.4函數(shù)的嵌套調(diào)用
6.4
函數(shù)的遞歸調(diào)用1.函數(shù)遞歸調(diào)用的概念函數(shù)的遞歸調(diào)用就是當一個函數(shù)在執(zhí)行的過程中,出現(xiàn)了直接或間接地調(diào)用函數(shù)本身的函數(shù)調(diào)用方式。下面定義求n!的函數(shù)定義。longfact(longn){if(n==1)return1;returnfact(n-1)*n;//出現(xiàn)了函數(shù)fact自己直接調(diào)用本}//身的函數(shù)調(diào)用要正確地理解函數(shù)的遞歸調(diào)用時,程序執(zhí)行的流程和返回點。256.4函數(shù)的嵌套調(diào)用
遞歸是用自己定義自己的過程,有時稱為循環(huán)定義(circulardefinition)。遞歸的例子很多。例如,整數(shù)的一個遞歸定義是:0,1,2,3,4,5,6,7,8,9加或減一個整數(shù)是整數(shù)。因此,15是8加7,21是9加12,12是9加2,等等。266.4函數(shù)的嵌套調(diào)用
函數(shù)調(diào)用自己時,在棧上為局部變量和參量分配存儲空間,從頭執(zhí)行函數(shù)代碼。遞歸調(diào)用并不復制函數(shù)代碼,只是新分配相應變量。每個遞歸調(diào)用返回時,其局部量和參數(shù)的存儲空間都釋放回棧中,執(zhí)行在函數(shù)中的調(diào)用點繼續(xù)。
許多函數(shù)的遞歸版本比等價的疊代版本運行得慢,原因在于反復調(diào)用得開銷太大。實際上,過分遞歸可以溢出堆棧。遞歸函數(shù)的主要優(yōu)點是能夠生成某些算法的更清晰、更簡潔的版本。如快速排序算法、漢諾塔問題等就很難用疊代方法實現(xiàn)。此外,某些問題(特別是人工智能有關的問題)本質(zhì)上是遞歸的,特別適合遞歸解。最后,有些人認為遞歸比疊代更便于思考。276.4函數(shù)的嵌套調(diào)用
2.函數(shù)遞歸調(diào)用的條件
遞歸調(diào)用的條件也是我們在定義一個遞歸函數(shù)時應該遵循的原則。(1)必須有完成函數(shù)任務的語句。如:上例求n!中的return1;(2)有一個確定是否能避免遞歸調(diào)用的測試條件。如果條件不滿足時就遞歸調(diào)用,否則就不再遞歸調(diào)用。(3)有一個遞歸調(diào)用語句,并且該遞歸調(diào)用語句的參數(shù)應該逐漸逼近不滿足條件,以致最后斷絕遞歸。(4)先測試,后遞歸調(diào)用。在遞歸函數(shù)定義中,必須先測試,后遞歸調(diào)用。也就是說,遞歸是有條件的,滿足了條件后,才可以遞歸。286.4函數(shù)的嵌套調(diào)用
Demos:遞歸函數(shù)例7.cpp猴子吃桃問題的遞歸解決.cpp遞歸函數(shù)例3.cpp遞歸函數(shù)例4.cpp,遞歸函數(shù)例1.cpp遞歸函數(shù)例2.cpp,遞歸函數(shù)例6.C遞歸函數(shù)例-整數(shù)的逆向輸出.cpp遞歸函數(shù)實例.cpp
牛數(shù)的遞歸算法2.cpp,牛數(shù)的遞歸算法1.cpp漢諾塔問題.cpp,遞歸函數(shù)例5.cpp,遞歸函數(shù)例子.cpp走臺階問題.cpp
最大公約數(shù)的遞歸解法.cpp
遞歸求滿足不等式的n值.cpp
十進制轉化為二進制遞歸解法.cpp29內(nèi)容提要函數(shù)的定義函數(shù)的調(diào)用函數(shù)的嵌套調(diào)用函數(shù)的遞歸調(diào)用局部變量和全局變量全局函數(shù)和靜態(tài)函數(shù)
第6章
函數(shù)306.5局部變量和全局變量
6.5局部變量和全局變量從程序中各個變量起作用的范圍(作用域)來看,變量可以分為局部變量和全局變量。1.局部變量在一個函數(shù)的內(nèi)部定義的變量就是內(nèi)部變量(局部變量)。如:
floatf1(inta){
int
b,c;//a,b,c有效
……}voidmain(void){
int
n,m;//m,n有效
……}31對局部變量作以下幾點說明:(1)局部變量的作用范圍(作用域):只局限在定義它的本函數(shù)體之內(nèi)。(2)局部變量的生存期(存在的時間):只有當程序執(zhí)行到本函數(shù)時,才給這些局部變量分配存儲單元,當本函數(shù)執(zhí)行完畢后,這些局部變量所占存儲單元就被釋放。(3)不同函數(shù)體中可以定義相同名字的變量,但它們代表不同的對象,互不干擾。它們在內(nèi)存占用不同的內(nèi)存單元。(4)函數(shù)的形式參數(shù)也是該函數(shù)的局部變量,其他函數(shù)不能調(diào)用。(5)在一個函數(shù)內(nèi)部,可以在復合語句中定義變量,但這些變量只在本復合語句中有效,因此,復合語句也可稱為“分程序”或“程序塊”。6.5局部變量和全局變量32(6)局部變量又可稱自動變量(auto),(因為可以用關鍵字auto說明之)。使用auto存儲類型定義的變量稱為自動變量,編譯系統(tǒng)在堆棧區(qū)(內(nèi)存的一部分)為它分配內(nèi)存空間。分配和釋放空間的操作都由系統(tǒng)自動完成,故稱為自動變量。函數(shù)內(nèi)定義的自動變量關鍵字auto可以缺省。6.5局部變量和全局變量332.靜態(tài)局部變量(局部靜態(tài)變量)
定義方法是:在函數(shù)體內(nèi)定義變量采用:
static類型標識符變量名;特點:
(1)靜態(tài)局部變量本身也是局部變量,因此其作用域也是局限在定義它的本函數(shù)體內(nèi),當離開本函數(shù)體,該變量就不再起作用,但其值還繼續(xù)保留。(2)另一方面,靜態(tài)局部變量又是靜態(tài)存儲類別的變量,所以,在整個程序運行開始就被分配固定的存儲單元(占用靜態(tài)存儲區(qū)),整個程序運行期間不再被重新分配,所以其生存期是整個程序運行期間。(3)靜態(tài)局部變量的賦初值的時間在編譯階段,并不是每發(fā)生一次函數(shù)調(diào)用就賦一次初值。當再次調(diào)用該函數(shù)時,靜態(tài)局部變量保留上次調(diào)用函數(shù)時的值。//Demo:static.cpp
6.5局部變量和全局變量343.全局變量
在所有函數(shù)體外部定義的變量為外部變量(全局變量),全局變量可以被本文件中其他函數(shù)所調(diào)用(使用)。全局變量的有效范圍為:從定義該變量的位置開始到本程序文件的結束。如:6.5局部變量和全局變量35intp=1,q=5;//全局變量floatf1(inta){
int
b,c;……//局部變量}charc1,c2; //全局變量charf2(intx,inty){
int
i,j;……}voidmain(void){
int
m,n;……}6.5局部變量和全局變量36對全局變量的幾點說明:(1)全局變量在程序的全部執(zhí)行過程中都占用固定的內(nèi)存儲單元,而不是僅在需要時才開辟單元,所以其生存期是整個程序運行期間。6.5局部變量和全局變量(2)全局變量的作用范圍是整個程序文件。全局變量處于文件的開頭定義時,其作用范圍為整個文件,否則在定義點之前的函數(shù)內(nèi)使用時,應在函數(shù)體內(nèi)或外部用extern說明。
37說明的格式是:
extern類型標識符變量名;//Demo:aboutglobal1.cppaboutglobal2.cpp6.5局部變量和全局變量38(3)在一個程序文件中定義的全局變量,要在同一程序的另外一個程序文件中使用時,應在使用它的程序文件中所有函數(shù)體內(nèi)部或外部對所使用的全局變量用extern說明(外部變量)。
//Demo:externvariation.cpp+myfun.h+myfun1.cpp+myfun2.cpp(4)在同一個文件中全局變量與局部變量同名時,則在局部變量的作用范圍內(nèi),全局變量不起作用。(可以使用域作用符::訪問全局變量)//Demo:域作用符.cpp6.5局部變量和全局變量394.靜態(tài)全局變量
當在所有函數(shù)體的外部用如下格式定義變量時,則這種變量稱為靜態(tài)全局變量。
static類型標識符變量名;靜態(tài)全局變量的特點是:(1)與全局變量基本相同,只是其作用范圍(即作用域)是定義它的程序文件,而不是整個程序。(2)靜態(tài)全局變量屬于靜態(tài)存儲類別的變量,所以它在程序一開始運行時,就被分配固定的存儲單元,所以其生存期是整個程序運行期間。(3)使用靜態(tài)全局變量的好處是同一程序的兩個不同的程序文件中可以使用相同名稱的變量名,而互不干擾。6.5局部變量和全局變量40注:變量的類型還有寄存器類型(register)//Demo:aboutregister.cpp6.5局部變量和全局變量41小結:從變量作用域和生存期的角度出發(fā),把覆蓋了從定義點開始到整個程序結束的變量稱為具有全局作用域和全局壽命的變量,簡稱為“全局變量”(GlobalVariable),而把作用域和生存期只覆蓋了某個函數(shù)或某個復合語句的變量稱為具有局部作用域和局部壽命的變量,簡稱為“局部變量”(LocalVariable),它包含如下存儲類型的變量:自動變量、靜態(tài)局部變量、寄存器變量和形參(形參也是自動型,也可說明為寄存器變量)。(注意局部靜態(tài)變量的生存期是整個程序)在所有函數(shù)外定義的變量稱為外部變量,若將它的作用域限制在一個源文件內(nèi),需加上關鍵字static,稱為靜態(tài)全局變量。這兩種變量統(tǒng)稱為全局變量。6.5局部變量和全局變量42內(nèi)容提要函數(shù)的定義函數(shù)的調(diào)用函數(shù)的嵌套調(diào)用函數(shù)的遞歸調(diào)用局部變量和全局變量全局函數(shù)和靜態(tài)函數(shù)
第6章
函數(shù)436.6全局函數(shù)和靜態(tài)函數(shù)1.全局函數(shù)(類似全局變量)
凡程序中定義的函數(shù),如果未做特別說明,一律都是全局的。也就是說,函數(shù)從本質(zhì)上是全局的,一個程序不管有多少個程序文件所組成,在某個程序文件中可以調(diào)用同一程序的另外一個程序文件中定義的函數(shù)。(可以缺省extern關鍵字),只要對被調(diào)函數(shù)的原型進行說明即可。6.6全局函數(shù)和靜態(tài)函數(shù)44聲明函數(shù)原型的語句:
類型標識符函數(shù)名(形參類型表);如:假設程序中定義了max函數(shù),則:int
max(int,int);就是對函數(shù)max原型的聲明。//Demos:函數(shù)原型.cpp
externvariation.cpp+myfun.h+myfun1.cpp+myfun2.cpp6.6全局函數(shù)和靜態(tài)函數(shù)452.靜態(tài)函數(shù)因為函數(shù)多數(shù)為外部型的,必然產(chǎn)生不同源文件中同名函數(shù)的沖突。若將某一重要函數(shù)定義為靜態(tài)型(static),則只能被該函數(shù)所在文件的其它函數(shù)調(diào)用,而不能被其它源文件的函數(shù)調(diào)用。靜態(tài)函數(shù)定義方法為:static類型標識符函數(shù)名(形參及其類型){
函數(shù)體}注意:這種函數(shù)就只能在定義它的程序文件中調(diào)用。6.6全局函數(shù)和靜態(tài)函數(shù)46內(nèi)容提要內(nèi)聯(lián)函數(shù)函數(shù)重載默認參數(shù)的函數(shù)函數(shù)指針函數(shù)與數(shù)組、指針及引用等的關系命名空間
第6章
函數(shù)476.7內(nèi)聯(lián)函數(shù)1.內(nèi)聯(lián)函數(shù)的定義方法和格式:
inline
函數(shù)值的類型函數(shù)名(形參及其類型列表){
函數(shù)體
}6.7內(nèi)聯(lián)函數(shù)48#include<iostream>usingnamespacestd;inlinedoublesquare(doublex){returnx*x;}voidmain(void){doublex;
cout<<”inputadata”;cin>>x;
cout<<”thesqureis“<<square(x);}6.7內(nèi)聯(lián)函數(shù)49
2.內(nèi)聯(lián)函數(shù)與普通函數(shù)的區(qū)別和聯(lián)系(1)在定義內(nèi)聯(lián)函數(shù)時,函數(shù)值的類型左面有“inline”關鍵字,而普通函數(shù)在定義時沒有此關鍵字。(2)程序中調(diào)用內(nèi)聯(lián)函數(shù)與調(diào)用普通函數(shù)的方法相同。(3)當在程序中調(diào)用一個內(nèi)聯(lián)函數(shù)時,是將該函數(shù)的代碼直接插入到調(diào)用點,然后執(zhí)行該段代碼,所以在調(diào)用過程中不存在程序流程的跳轉和返回問題。而普通函數(shù)的調(diào)用,程序是從主調(diào)函數(shù)的調(diào)用點轉去執(zhí)行被調(diào)函數(shù),待被調(diào)函數(shù)執(zhí)行完畢后,再返回到主調(diào)函數(shù)的調(diào)用點的下一語句繼續(xù)執(zhí)行。6.7內(nèi)聯(lián)函數(shù)50
(4)從調(diào)用機理看,內(nèi)聯(lián)函數(shù)可加快程序代碼的執(zhí)行速度和效率,但這是以增加程序代碼為代價來求得速度的。6.7內(nèi)聯(lián)函數(shù)513.對內(nèi)聯(lián)函數(shù)的限制應注意:不是任何一個函數(shù)都可定義成內(nèi)聯(lián)函數(shù)。(1)內(nèi)聯(lián)函數(shù)的函數(shù)體內(nèi)不能含有復雜的結構控制語句,如:switch和while,如果內(nèi)聯(lián)函數(shù)的函數(shù)體內(nèi)有這些語句,則編譯將該函數(shù)視同普通函數(shù)那樣產(chǎn)生函數(shù)調(diào)用代碼。(2)遞歸函數(shù)不能被用來作為內(nèi)聯(lián)函數(shù)。(3)內(nèi)聯(lián)函數(shù)一般適合于只有1~5行語句的小函數(shù),對一個含有很多語句的大函數(shù),沒有必要使用內(nèi)聯(lián)函數(shù)來實現(xiàn)。6.7內(nèi)聯(lián)函數(shù)52
6.8函數(shù)重載1.什么是函數(shù)重載函數(shù)重載是指一個函數(shù)可以和同一作用域中的其他函數(shù)具有相同的名字,但這些同名函數(shù)的參數(shù)類型、參數(shù)個數(shù)、返回值、函數(shù)功能可以完全不同。如:6.8函數(shù)重載53
#include<iostream>usingnamespacestd;voidwhatitis(inti){
cout<<"thisisinteger"<<i<<endl;}voidwhatitis(charc[]){
cout<<“thisisstring”<<c<<endl;}voidmain(void){
inti=1;charc[]="abcdef";
whatitis(i);
whatitis(c);}6.8函數(shù)重載54內(nèi)容提要內(nèi)聯(lián)函數(shù)函數(shù)重載默認參數(shù)的函數(shù)函數(shù)指針函數(shù)與數(shù)組、指針及引用等的關系命名空間
第6章
函數(shù)55在本例中定義了兩個名稱都叫whatitis的函數(shù),但它們的形參類型不同。因此,這兩個函數(shù)就是重載函數(shù)。2.為什么要使用函數(shù)重載在原有C語言中,每個函數(shù)必須有其唯一的名稱,這樣的缺點是所有具有相同功能、而只是函數(shù)參數(shù)不一樣的函數(shù),就必須用一個不同的名稱,而C++中采用了函數(shù)重載后,對于具有同一功能的函數(shù),如果只是由于函數(shù)參數(shù)類型不一樣,則可以定義相同名稱的函數(shù)。6.8函數(shù)重載563.匹配重載函數(shù)的順序由于重載函數(shù)具有相同的函數(shù)名,在進行函數(shù)調(diào)用時,系統(tǒng)一般按照調(diào)用函數(shù)時的參數(shù)個數(shù)、類型和順序來確定被調(diào)用的函數(shù)。具體來說,按以下三個步驟的先后次序找到并調(diào)用那個函數(shù):(1)尋找一個嚴格的匹配,即:調(diào)用與實參的數(shù)據(jù)類型、個數(shù)完全相同的那個函數(shù)。(2)通過內(nèi)部轉換尋求一個匹配,即:通過(1)的方法沒有找到相匹配的函數(shù)時,則由C++系統(tǒng)對實參的數(shù)據(jù)類型進行內(nèi)部轉換,轉換完畢后,如果有匹配的函數(shù)存在,則執(zhí)行該函數(shù)。(3)通過用戶定義的轉換尋求一個匹配,若能查出有唯一的一組轉換,就調(diào)用那個函數(shù)。即:在函數(shù)調(diào)用處由程序員對實參進行強制類型轉換,以此作為查找相匹配的函數(shù)的依據(jù)。6.8函數(shù)重載57#include<iostream>usingnamespacestd;voidprint(doubled){
cout<<"thisisadouble"<<d<<"\n";}voidprint(inti){
cout<<"thisisaninteger"<<i<<"\n";}voidmain(void){
intx=1,z=10;floaty=1.0;charc='a';
print(x); //按規(guī)則(1)自動匹配函數(shù)voidprint(inti)
print(y); //按規(guī)則(2)通過內(nèi)部轉換匹配函數(shù)
//voidprint(doublei)6.8函數(shù)重載58//因為系統(tǒng)能自動將float型轉換成double型
print(c); //按規(guī)則(2)通過內(nèi)部轉換匹配函數(shù)
//voidprint(inti)//因為系統(tǒng)能自動將char型轉換成int型
print(double(z));//按規(guī)則(3)匹配//voidprint(doublei)因為程序中將實參z強制轉換//為double型。}6.8函數(shù)重載594.定義重載函數(shù)時的注意事項(1)重載函數(shù)間不能只是函數(shù)的返回值不同,應至少在形參的個數(shù)、參數(shù)類型或參數(shù)順序上有所不同。如:6.8函數(shù)重載voidmyfun(inti){………………}int
myfun(inti){………………}這種重載就是錯誤的。(2)應使所有的重載函數(shù)的功能相同。如果讓重載函數(shù)完成不同的功能,會破壞程序的可讀性。60內(nèi)容提要內(nèi)聯(lián)函數(shù)函數(shù)重載默認參數(shù)的函數(shù)函數(shù)指針函數(shù)與數(shù)組、指針及引用等的關系命名空間
第6章
函數(shù)616.9默認參數(shù)的函數(shù)1.默認參數(shù)的函數(shù)C++允許在定義函數(shù)時給其中的某個或某些形式參數(shù)指定默認值,這樣,當發(fā)生函數(shù)調(diào)用時,如果省略了對應位置上的實參的值時,則在執(zhí)行被調(diào)函數(shù)時,以該形參的默認值進行運算。如:6.9默認參數(shù)的重載62#include<iostream>usingnamespacestd;voidsum(intnum=10){//形參默認值
int
i,s=0;
for(i=1;i<=num;i++)s=s+i;
cout<<"sumis"<<s<<"\n";}voidmain(void){sum(100);//提供了實參值,被調(diào)函數(shù)以100進行運算,//輸出結果為5050sum();//省略實參值,使用形參默認值10,輸出結}//果為556.9默認參數(shù)的重載632.使用默認參數(shù)的函數(shù)的注意事項(1)默認參數(shù)一般在函數(shù)說明中提供。如果程序中既有函數(shù)的說明又有函數(shù)的定義時,則定義函數(shù)時不允許再定義參數(shù)的默認值。如果程序中只有函數(shù)的定義,而沒有說明函數(shù),則默認參數(shù)才可出現(xiàn)在函數(shù)定義中。如:voidpoint(intx=10,y=20);voidmain(void){…………}voidpoint(intx,inty){
cout<<x<<endl;
cout<<y<<endl;
}6.9默認參數(shù)的重載64(2)默認參數(shù)的順序:如果一個函數(shù)中有多個默認參數(shù)時,則形參分布中,默認參數(shù)應從右至左連續(xù)定義,即指定和不指定不能交叉。如:voidmyfunc(inta=1,floatb,longc=20); //錯誤voidmyfunc(int
a,floatb=2.1,longc=30); //正確(3)當進行調(diào)用時,實參數(shù)目少于形參時,編譯系統(tǒng)按從右到左的順序用默認值來補足所缺少的實參。(從左到右使用實參,右邊剩余的使用默認參數(shù))//Demo:函數(shù)的默認參數(shù).cpp6.9默認參數(shù)的函數(shù)65內(nèi)容提要內(nèi)聯(lián)函數(shù)函數(shù)重載默認參數(shù)的函數(shù)函數(shù)與指針函數(shù)與數(shù)組及引用等的關系命名空間
第6章
函數(shù)66函數(shù)與指針的關系非常緊密,在學習函數(shù)之后,我們應該理解和掌握函數(shù)與指針的各種關系。1.指針作為函數(shù)的參數(shù)2.函數(shù)返回指針類型3.使用指向函數(shù)的指針6.10函數(shù)與指針671.指針作為函數(shù)的參數(shù)#include<iostream>usingnamespacestd;voidfun(int*pi){ (*pi)++;}voidmain(void){
inti=100;
int*p=&i;
fun(p);
cout<<"i="<<i<<endl;}思考:程序的輸出?6.10函數(shù)與指針68#include<iostream>usingnamespacestd;voidfun(int*pi){ (*pi)++;}voidmain(void){
inta[]={1,2,3,4,5};
int*p=a+3;
fun(p);
for(inti=0;i<sizeof(a)/sizeof(int);i++)cout<<a[i]<<""; }思考:程序的輸出?6.10函數(shù)與指針69#include<iostream>usingnamespacestd;voidfun(int*p){ p++;}voidmain(void){
inta[]={1,2,3,4,5};
int*q=a;
cout<<"*q="<<*q<<endl;
fun(q);
cout<<"*q="<<*q<<endl; }思考:程序的輸出?如何使p的變化帶回給q?6.10函數(shù)與指針70#include<iostream>usingnamespacestd;voidfun(int*&p){//對指針類型變量的引用,作為參數(shù) p++;}voidmain(void){
inta[]={1,2,3,4,5};
int*q=a;
cout<<"*q="<<*q<<endl;
fun(q); cout<<"*q="<<*q<<endl; }6.10函數(shù)與指針712.函數(shù)的返回值類型為指針類型#include<iostream>usingnamespacestd;int*fun(int
a[],intn){ staticintmax=a[0];//如果去掉static,能編譯通過嗎?
for(intk=1;k<n;k++)if(a[k]>max)max=a[k]; return&max;}voidmain(void){
inta[]={1,2,3,14,5};
int*pmax;
pmax=fun(a,sizeof(a)/sizeof(int));
cout<<"*pmax="<<*pmax<<endl; }6.10函數(shù)與指針72注意:函數(shù)返回指針時,不能返回局部變量的指針??梢苑祷仂o態(tài)變量的指針,全局變量的指針以及動態(tài)存儲分配的地址。如:#include<iostream>usingnamespacestd;int*fun(void){
int*p=newint; returnp;}voidmain(void){
int*q=fun(); *q=100;
cout<<"*q="<<*q<<endl;}6.10函數(shù)與指針732.指向函數(shù)的指針可以定義一個指向函數(shù)的指針。定義格式為:函數(shù)返回值類型(*指向函數(shù)的指針名)(參數(shù)列表)如:int(*pfun)(int,int);聲明了一個指向返回值類型為int,帶兩個int參數(shù)的指針pfun。該如何使用pfun呢?6.10函數(shù)與指針74使用pfun的方法同其它指針變量。注意:使用指針變量前,一定要確定該指針變量有所指!通過pfun可以調(diào)用它所指向的函數(shù)。使用方法如下:
pfun(實參);如:int
sum(int
x,inty){returnx+y;}
int(*pfun)(int,int);//聲明pfun
pfun=sum;//pfun有所指
cout<<pfun(12,40)<<endl;//使用pfun6.10函數(shù)與指針75#include<iostream>usingnamespacestd;int
sum(int
a,intb){returna+b;}voidmain(void){
int(*pfun)(int,int);
pfun=sum;//初始化指針變量pfun
intc=pfun(10,20);
cout<<"c="<<c<<endl; }6.10函數(shù)與指針76指向函數(shù)的指針變量可以作為某一個函數(shù)的參數(shù)。這樣,當傳遞給該指針參數(shù)(指向函數(shù))不同的實參值時,就可以通過使用該指向函數(shù)的指針參數(shù),而達到調(diào)用不同函數(shù)的目的。如:6.10函數(shù)與指針77#include<iostream>usingnamespacestd;int
sum(int
a,intb){returna+b;}int
max(int
x,inty){ returnx>y?x:y;}int
fun(int
xx,int
yy,int(*pfun)(int
xx,int
yy)){
inttemp; temp=pfun(xx,yy); returntemp;}voidmain(void){
int(*p)(int,int);p=sum;cout<<fun(10,20,p)<<endl;//調(diào)用sum函數(shù) p=max;cout<<fun(10,20,p)<<endl; //調(diào)用max函數(shù) }6.10函數(shù)與指針78類似地,可以使用指向函數(shù)的指針數(shù)組。#include<iostream>usingnamespacestd;typedef
int(*PFunType)(int,int);//定義指向函數(shù)的指針類型PFunTypeint
sum(int
a,intb){returna+b;}int
max(int
x,inty){ returnx>y?x:y;}int
fun(int
xx,int
yy,int(*pfun)(intxx,int
yy)){
inttemp=pfun(xx,yy); returntemp;}voidmain(void){
PFunTypep[]={sum,max};//函數(shù)指針數(shù)組初始化
//等價于int(*p[2])(int,int)={sum,max};
cout<<fun(10,20,p[0])<<endl;//使用指針數(shù)組元素p[0]調(diào)用sum
cout<<fun(10,20,p[1])<<endl;//使用指針數(shù)組元素p[1]調(diào)用max}6.10函數(shù)與指針79main()的變元argc和argv(命令行參數(shù))//已經(jīng)在指針與引用一章講述
有時,需要向程序傳入信息。我們一般
通過命令行向主函數(shù)main()傳遞信息。命令行變元(commandlineargument)是操作系統(tǒng)命令行中,執(zhí)行程序名字之后的信息。例如,在UNIX系統(tǒng)下編譯C程序時,在提示符下鍵入類似下行的內(nèi)容。
cc
program_name
其中,program_name是準備被編譯的程序。程序名字program_name作為參數(shù)傳給命令cc(編譯程序)。6.10函數(shù)與指針80類似地,C++的源程序經(jīng)編譯、鏈接后生成了可執(zhí)行的程序(如:myprogram.exe)后,允許向該程序傳送參數(shù),形式為D:\ms\>myprogrampara1para2…paraN
那么,該如何給C++程序傳遞參數(shù)呢?6.10函數(shù)與指針81
main(int
argc,char*argv[]))函數(shù)中的兩個參數(shù)用于接受運行程序時命令行傳入的參數(shù)信息,一個是argc,另一個是argv。
argc是整型變量,用于存放命令行中參數(shù)的總數(shù)(因為程序名也計算在內(nèi),argc的值最小為1)。形參argv是一個指針數(shù)組,指針數(shù)組中的每個元素(是一個指針)都分別指向相應的一個命令行變元(字符串)。6.10函數(shù)與指針82如:D:\>myprogrampara1para2para3則argc值為4,指針argv[0]指向命令行參數(shù)myprogram(即程序名),指針argv[1]指向命令行參數(shù)para1,指針argv[2]指向命令行參數(shù)para2,指針argv[3]指向命令行參數(shù)para3。
//Demos:
aboutmain.cpp程序設計其他問題面試題.cpp6.10函數(shù)與指針83內(nèi)容提要內(nèi)聯(lián)函數(shù)函數(shù)重載默認參數(shù)的函數(shù)函數(shù)與指針函數(shù)與數(shù)組及引用等的關系命名空間
第6章
函數(shù)84函數(shù)與數(shù)組及引用等的關系,請參考上章“指針與引用”中的相關介紹。這里不再重敘。6.11命名空間85內(nèi)容提要內(nèi)聯(lián)函數(shù)函數(shù)重載默認參數(shù)的函數(shù)函數(shù)與指針函數(shù)與數(shù)組及引用等的關系命名空間
第6章
函數(shù)86本節(jié)討論在C++標準中介紹的命名空間的基本概念。命名空間提供了一種在程序內(nèi)和程序之間組織和使用名稱的技術。1.背景給人和物命名可能是困難的。在家庭內(nèi)部可以說出不同的家庭成員的名稱,比如John、George、Ann和Alice。在家庭內(nèi),當說到Ann的時候,每個人都知道談論的是誰。然而在家庭之外,有許多名叫Ann的人。當需要在家庭外部談論她的時候,可能需要限定她的名稱,需要說明談論的是哪一個Ann,否則有人可能想到另一個名為Ann的人。6.11命名空間87為了限制談論的是哪一個Ann,一種方法是將她與家庭名稱相聯(lián)系。例如,在Washingtons家庭內(nèi)部,每個人都用Ann的名字稱呼她;在Nguyens家庭內(nèi)部,每個人也都用Ann的名字稱呼這個家庭的Ann。但是在家庭外部,她們被稱為”Washingtons,Ann”和”Nguyens,Ann”。分開姓和名的逗號稱為家庭分辨操作符。在編程的過程中,特別對于大型程序而言,也有相同的問題。我們需要命名程序內(nèi)的常數(shù)、變量、函數(shù)和其他對象。但是當我們自己、其他項目組成成員或者系統(tǒng)程序員將我們的程序與其他程序結合在一起時,將出現(xiàn)什么情況?有些名稱可能用在不止一個函數(shù)或者對象中?,F(xiàn)在遇到了麻煩,如果兩個程序段使用相同的名稱—比如num—來定義一個整數(shù),那么當引用num時,究竟指的是哪一個num是不清楚的。6.11命名空間88為了解決這個問題,C++定義了命名空間。命名空間是屬于相同組的名稱的集合。例如,可以有兩個組:G1和G2。如果在每個組內(nèi)定義一個名為num的變量,那么就可以沒有任何歧義地在G1內(nèi)部或者在G2內(nèi)部引用num。但是如果需要在組外引用num,則必須用作用域分辨符(::)來限定名稱。換句話說,G1內(nèi)的num叫G1::num,而G2內(nèi)的num叫G2::num。下圖顯示出C++如何使用命名空間來定義命名空間。namespaceG1namespaceG2{{intnum;intnum;… …}//namespaceG1}//namespaceG2G1::num=5;G2::num=10;6.11命名空間89為了使這個概念清晰,現(xiàn)在編寫一個非常不尋常的程序。雖然永遠不建議這樣做,但是這里還是編寫了一個兩次使用名稱cout的程序。第一個cout是一個變量名(值為5)的名稱,因為它沒有使用作用域分辨操作符,所以它的作用域局限于程序中的main。第二個cout使用了作用域分辨操作符,它將cout名稱與std命名空間相聯(lián)系,該命名空間定義所有在c++程序庫中使用的名稱。當使用cout時,編譯器知道它應該檢查程序內(nèi)的聲明,當使用std::cout時,該程序在我們的程序內(nèi)找不到這個全稱(姓和名),因此它嘗試在頭文件內(nèi)尋找,并且在頭文件<iostream>內(nèi)發(fā)現(xiàn)了這個名稱。以下程序包含這個程序的代碼和結果。6.11命名空間90/*Demonstratenamespacescope.*/#include<iostream>intmain(){
int
cout=5;
std::cout<<cout<<“\n”;return0;}//mainResult:5程序證明:cout和std::cout是完全不同的兩個名稱。一個屬于全局命名空間,另一個屬于std命名空間。6.11命名空間91為了進一步研究,現(xiàn)在編寫一個僅使用cout作為輸出流名稱的程序。//Demonstratenotinscopeerror.#include<iostream>intmain(){
cout<<“Hello\n”;return0;}//mainResults:Error:undefinedidentifier‘cout0’這個程序不能編譯,因為編譯器要尋找cout的聲明,但是卻沒有發(fā)現(xiàn)。它既沒有在程序內(nèi),也沒有在iostream文件內(nèi)發(fā)現(xiàn)cout的聲明。iostream文件使用的是std::cout,而不是cout。6.11命名空間922.使用命名空間的名稱為了使用特定命名空間的名稱,有3種選擇:寫出全稱、添加使用命令或者添加使用聲明。(1)全稱可能解決這個問題最簡單的方法就是使用全稱。盡管這樣更簡單,但是它需要更多的擊鍵,而且程序更長。當使用全稱時要將該命名空間的家族名稱(比如std)和作用域分辨操作符添加到名稱上。因此,cout變成std::cout。如:#include<iosteam>voidmain(){
std:cout<<“Enteraninteger:”;
int
numIn;
std:cin>>numIn;
std::cout<<“Youentered:“<<numIn<<“\n”;}6.11命名空間93(2)使用命令第2種解決方法是添加名為使用命令的語句,通常將其放在包含語句后面的程序全局區(qū)域。語句格式如下所示。它必須以分號結束。usingnamespacename_of_namespace;當編譯器遇到未聲明的名稱時,它就將using命令定義的命名空間的名稱添加到未聲明的名稱上,然后試圖發(fā)現(xiàn)這個全稱的生命。我們這次使用命名空間命令來命令編譯器,為所有找不到的名稱使用std命名空間。6.11命名空間94#include<iostream>usingnamespacestd;voidmain(){
cout<<“Enteraninteger:”;
int
numIn;
cin>>numIn;
cout<<“Youentered:“<<numIn<<“\n”;}//main6.11命名空間95(3)使用聲明使用命令的方法將命名空間的名稱添加到每一個編譯器找不到的名稱。第三種解決方法—使用聲明,對編譯器試圖解析的名稱進行了限制。它告訴編譯器只將命名空間添加到選定數(shù)量的名稱上,而不是全部找不到的名稱上。其格式如下:usingname_of_the_namespace::identifier;當編譯器遇到的名稱包含在using聲明內(nèi)聲明的標識符時,它就添加命名空間的名稱,并再次嘗試。例如,下面程序增加了兩條使用命名空間的聲明,來命令編譯器只將std添加到cin、cout和endl;6.11命名空間96#include<iostream>usingstd::cout;usingstd::cin;usingstd::endl;voidmain(){
cout<<“Enteraninteger:”;
int
numIn;
cin>>numIn;
cout<<“Youentered:“<<numIn<<“\n”;}//main6.11命名空間97(4)命令和聲明之間的區(qū)別使用聲明將它的名稱添加到局部作用域,使用命令使名稱在聲明她們的作用域內(nèi)(通常是編譯單元)可以使用。命名空間的命令和聲明之間的另一個主要區(qū)別是,using語句包括的名稱數(shù)量不同。命令添加所有命名空間內(nèi)的名稱,而聲明只添加指定的名稱。通常使用聲明更安全,尤其是在多于一個名稱空間時??匆粋€例子,假設有兩個命名空間:purchasing和inventory。她們在程序內(nèi)聲明,都有兩個普通的名稱:i和j。這里想使用來自purchasing的i和來自inventory的j。如果在這種情況下使用命令,編譯器將產(chǎn)生錯誤。但是,聲明就可以限制能夠使用的變量,并且不會出現(xiàn)錯誤。命令編譯器每當發(fā)現(xiàn)i時就使用purchasing::i,而每當發(fā)現(xiàn)j時就使用inventory::j。6.11命名空間98#include<iostream>usingnamespacestd;namespacepurchasing{
inti;intj;}//purchasingnamespacenamespaceinventory{
inti;intj;}//inventorynamespaceusingpurchasing::i;usinginventory::j;//usingnamespaceinventory;voidmain(){i=5;cout<<“Purchasingiis:”<<purchasing::i<<endl;j=12;cout<<“Inventoryjis:”<<inventory::j<<endl;
cout<<i<<j<<std::endl;}//main6.11命名空間994.聲明命名空間前面已經(jīng)非正式地說明了如何聲明命名空間
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
- 4. 未經(jīng)權益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責。
- 6. 下載文件中如有侵權或不適當內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 2024年度企業(yè)租賃個人車輛協(xié)議書樣本
- 委托合同:項目委托管理協(xié)議
- 2024年商品房代理銷售協(xié)議合同范本
- 2024年閱卷老師保密協(xié)議
- 標準工業(yè)產(chǎn)品買賣合同樣本
- 電子購銷合同范本2024年
- 建設工程石材供應合同法律風險
- 那個星期天公開課一等獎創(chuàng)新教學設計
- 試用合同范本
- 履約擔保協(xié)議書
- 干部人事檔案任前審核登記表范表
- 北京市道德與法治初一上學期期中試卷及答案指導(2024年)
- 高校實驗室安全基礎學習通超星期末考試答案章節(jié)答案2024年
- 四川省綿陽市高中2025屆高三一診考試物理試卷含解析
- 國開2024年《中國法律史》平時作業(yè)1-3答案
- DZ∕T 0283-2015 地面沉降調(diào)查與監(jiān)測規(guī)范(正式版)
- 朗致集團邏輯測評試卷2024
- 井式爐課程設計說明書
- 用友銀企聯(lián)云服務ppt課件
- 造價審核部崗位職責(共4篇)
- 世界機場四字代碼
評論
0/150
提交評論