C++程序設(shè)計(jì)語(yǔ)言課件_第1頁(yè)
C++程序設(shè)計(jì)語(yǔ)言課件_第2頁(yè)
C++程序設(shè)計(jì)語(yǔ)言課件_第3頁(yè)
C++程序設(shè)計(jì)語(yǔ)言課件_第4頁(yè)
C++程序設(shè)計(jì)語(yǔ)言課件_第5頁(yè)
已閱讀5頁(yè),還剩1019頁(yè)未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

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

文檔簡(jiǎn)介

數(shù)2.1函數(shù)的定義與使用

在編輯一個(gè)大型程式時(shí),即使各個(gè)函數(shù)的前後順序不同,程式執(zhí)行的開(kāi)始點(diǎn)永遠(yuǎn)是主函數(shù)。主函數(shù)按照調(diào)用與被調(diào)用關(guān)係調(diào)用子函數(shù)。子函數(shù)如果與其它子函數(shù)又存在調(diào)用與被調(diào)用關(guān)係,當(dāng)然還可以再調(diào)用其他子函數(shù)。

在一對(duì)調(diào)用與被調(diào)用關(guān)係中,我們把調(diào)用其他函數(shù)的函數(shù)稱(chēng)為主調(diào)函數(shù),被其他函數(shù)調(diào)用的函數(shù)稱(chēng)為被調(diào)函數(shù)。在一個(gè)較為複雜的大型程式中,一個(gè)函數(shù)很可能同時(shí)扮演兩種不同的角色——主調(diào)函數(shù)與被調(diào)函數(shù),即既調(diào)用別的函數(shù)(被調(diào)函數(shù))又被另外的函數(shù)(主調(diào)函數(shù))調(diào)用。函數(shù)一般應(yīng)遵守先定義後調(diào)用的原則,否則應(yīng)在調(diào)用函數(shù)中先進(jìn)行原形說(shuō)明。2.1.1函數(shù)的定義一個(gè)完整的函數(shù)定義由兩部分組成,即函數(shù)頭與函數(shù)體。1.函數(shù)定義的一般語(yǔ)法形式<類(lèi)型識(shí)別字><函數(shù)名說(shuō)明符>(形式參數(shù)表){

說(shuō)明性語(yǔ)句序列;實(shí)現(xiàn)函數(shù)功能的語(yǔ)句系列;}

函數(shù)頭是指上述格式中的<類(lèi)型識(shí)別字><函數(shù)名說(shuō)明符>(形式參數(shù)表)。其中函數(shù)名可由函數(shù)設(shè)計(jì)者命名,可以是任何一個(gè)不重複的合法的識(shí)別字(唯一的例外是,主函數(shù)必須命名為main)。函數(shù)體是指上述格式中被一對(duì)大括弧括起的複合語(yǔ)句部分。該函數(shù)所應(yīng)實(shí)現(xiàn)的功能由相應(yīng)的複合語(yǔ)句完成。2.函數(shù)的類(lèi)型和返回值函數(shù)頭部分的類(lèi)型識(shí)別字規(guī)定了函數(shù)的返回值類(lèi)型。函數(shù)的返回值是返回給主調(diào)函數(shù)的處理結(jié)果,由函數(shù)體部分的return語(yǔ)句帶回。例如,returnvalue1。無(wú)返回值的函數(shù)其類(lèi)型識(shí)別字為void,不必有return語(yǔ)句。3.形式參數(shù)函數(shù)頭部分的形式參數(shù)(簡(jiǎn)稱(chēng)形參)表的內(nèi)容如下:類(lèi)型l形參名1,類(lèi)型2形參名2,...,類(lèi)型n形參名n其中類(lèi)型1、類(lèi)型2、...、類(lèi)型n是類(lèi)型識(shí)別字,表示形參的數(shù)據(jù)類(lèi)型(int、double、float、char、bool等);形參名1、形參名2、...、形參名n是形參名(合法的自定義識(shí)別字)。形參是用來(lái)實(shí)現(xiàn)主調(diào)函數(shù)與被調(diào)函數(shù)之間的數(shù)據(jù)聯(lián)繫,通常將函數(shù)所處理的數(shù)據(jù)、影響函數(shù)功能的因素或者函數(shù)處理的結(jié)果作為形參。對(duì)於無(wú)形參的函數(shù),其形參表的內(nèi)容應(yīng)該為空,但代表函數(shù)的小括弧對(duì)不能省略。

函數(shù)在沒(méi)有被調(diào)用的時(shí)候其形參只是一個(gè)符號(hào),它標(biāo)誌著在形參出現(xiàn)的位置應(yīng)該有一個(gè)什麼類(lèi)型的數(shù)據(jù)。函數(shù)在被調(diào)用時(shí)才由主調(diào)函數(shù)將實(shí)際參數(shù)(簡(jiǎn)稱(chēng)實(shí)參)賦予形參。從這一點(diǎn)上說(shuō),C++中的函數(shù)與數(shù)學(xué)中的函數(shù)概念極其相似。例如,我們都熟悉的如下數(shù)學(xué)中的函數(shù)形式:

f(x)=3x2+5x-2

這個(gè)函數(shù)只有當(dāng)引數(shù)x被賦以確定的值以後,才能計(jì)算出函數(shù)的值。2.1.2函數(shù)的調(diào)用如果沒(méi)有遵守先定義後調(diào)用的原則,調(diào)用函數(shù)之前先要在主調(diào)函數(shù)中聲明函數(shù)原型。在主調(diào)函數(shù)中,或所有函數(shù)之前,按如下形式進(jìn)行函數(shù)原型聲明:

<類(lèi)型識(shí)別字><被調(diào)函數(shù)名>(含類(lèi)型說(shuō)明的形參表);

如果是在所有函數(shù)之前聲明了函數(shù)原型,那麼該函數(shù)原型在本程式檔中任何地方都有效,也就是說(shuō),在本程式檔中任何地方都可以依照該原型調(diào)用相應(yīng)的函數(shù)。如果是在某個(gè)主調(diào)函數(shù)內(nèi)部聲明了被調(diào)函數(shù)原型,那麼該原型就只能在這個(gè)函數(shù)內(nèi)部有效。聲明了函數(shù)原型之後,便可以按如下形式調(diào)用子函數(shù):

<函數(shù)名>(實(shí)參1,實(shí)參2,…,實(shí)參n)

實(shí)參列表中應(yīng)給出與函數(shù)原型中形參個(gè)數(shù)相同、類(lèi)型相符的實(shí)參,每個(gè)實(shí)參都可以是常量、變數(shù)或運(yùn)算式三者之一。實(shí)參與實(shí)參之間用逗號(hào)作為分隔符號(hào)。注意,這裏的逗號(hào)不是順序求值運(yùn)算符。函數(shù)調(diào)用可以作為一條語(yǔ)句,這時(shí)函數(shù)可以沒(méi)有返回值。函數(shù)調(diào)用也可以出現(xiàn)在運(yùn)算式中,這時(shí)就必須有一個(gè)明確的返回值。函數(shù)調(diào)用示例如下?!纠?-1】編寫(xiě)一個(gè)函數(shù),把華氏溫度轉(zhuǎn)換為攝氏溫度,公式為C=(F-32)*5/9,公式中F代表華氏溫度,C代表攝氏溫度。在主函數(shù)中提示用戶輸入一個(gè)華氏溫度,並完成輸入及輸出,由函數(shù)完成轉(zhuǎn)化功能。程式代碼如下:

#include<iostream.h>floathstoss(floatfHuashi);//原型說(shuō)明

voidmain(){floatfHuashi; cout<<endl<<"輸入一個(gè)華氏溫度值:"; cin>>fHuashi; cout<<"華氏"<<fHuashi <<"度對(duì)應(yīng)攝氏溫度"<<hstoss(fHuashi)<<"度"<<endl; //函數(shù)調(diào)用作為一個(gè)運(yùn)算式出現(xiàn)在輸出語(yǔ)句中}floathstoss(floatfHuashi){ floatfSheshi; fSheshi=(fHuashi-32)*5/9; return(fSheshi);}程式運(yùn)行結(jié)果為輸入一個(gè)華氏溫度值:68華氏68度對(duì)應(yīng)攝氏20度【例2-2】編寫(xiě)一個(gè)求x的n次方的函數(shù)。分析:求x的n次方,實(shí)際是求x自乘n次的乘積。程式代碼如下:#include<iostream.h>doublepower(doubledDishu,intiMi); //原型說(shuō)明voidmain(){ cout<<"底數(shù)1.8的3次冪是"<<power(1.8,3)<<endl; //函數(shù)調(diào)用作為一個(gè)運(yùn)算式出現(xiàn)在輸出語(yǔ)句中}doublepower(doubledDishu,intiMi){ intiCount; doubledResult=1.0; for(iCount=1;iCount<=iMi;iCount++) dResult=dResult*dDishu; return(dResult);}程式運(yùn)行結(jié)果為底數(shù)1.8的3次冪是5.832【例2-3】輸入一個(gè)8位的二進(jìn)位數(shù),將其轉(zhuǎn)換為十進(jìn)位數(shù)後再輸出。對(duì)於非法輸入(除0和1以外的任何字元)應(yīng)給出提示資訊。分析:將二進(jìn)位數(shù)轉(zhuǎn)換為十進(jìn)位數(shù),只要將二進(jìn)位數(shù)的每一位乘以該位的權(quán),然後相加。例如,110100112=1(27)+1(26)+0(25)+1(24)+0(23)+0(22)+1(21)+l(20)=21110,所以,如果輸入00001101,則應(yīng)輸出13??梢灾苯右美?-2中的函數(shù)power來(lái)求2的各次方。程式代碼如下:#include<iostream.h>doublepower(doubledDishu,intiMi); //函數(shù)原型說(shuō)明voidmain(){ intiCount=8; intiValue=0; charcChar; boolbFlag=true;cout<<"輸入一個(gè)8位的二進(jìn)位數(shù):"; while(iCount>0) { cin>>cChar; if(cChar!='1'&&cChar!='0') { cout<<"這不是一個(gè)二進(jìn)位數(shù)!不能正確轉(zhuǎn)換"<<endl; bFlag=false; } if(cChar=='1') iValue=iValue+int(power(2,iCount-1));iCount--; } if(bFlag) cout<<"十進(jìn)位值為:"<<iValue<<endl;}doublepower(doubledDishu,intiMi){ intiCount; doubledResult=1.0; for(iCount=1;iCount<=iMi;iCount++) dResult=dResult*dDishu; return(dResult);}

輸入符合要求時(shí)(僅有字元0和1)的程式運(yùn)行結(jié)果為輸入一個(gè)8位的二進(jìn)位數(shù):11010011

十進(jìn)位值:211

輸入不符合要求時(shí)(含有除0和1以外的任何字元)的程式運(yùn)行結(jié)果為輸入一個(gè)8位的二進(jìn)位數(shù):110lao11

這不是一個(gè)二進(jìn)位數(shù)!不能正確轉(zhuǎn)換【例2-4】編寫(xiě)一個(gè)函數(shù)可用來(lái)判斷任給的一個(gè)正整數(shù)是否為素?cái)?shù)(或質(zhì)數(shù))。再編寫(xiě)主程序完成輸入、調(diào)用和輸出。素?cái)?shù)是指只能被1和它自身整除的數(shù)。分析:素?cái)?shù)的逆定義就是,一但某數(shù)n能被2、3、...、n-1中的任何一個(gè)數(shù)除盡(只要除法中有一次餘數(shù)為零),則n肯定不是一個(gè)素?cái)?shù);某數(shù)n若依次除以2、3、...、n-1,結(jié)果都除不盡(有餘數(shù)),則n肯定是一個(gè)素?cái)?shù)。程式代碼如下:#include<iostream.h>intiIsprime(intiNum);voidmain(){ intiNum; cout<<"請(qǐng)輸入一個(gè)正整數(shù):"; cin>>iNum; if(iIsprime(iNum)==1) cout<<iNum<<"是一個(gè)素?cái)?shù)."<<endl;else cout<<iNum<<"不是一個(gè)素?cái)?shù)."<<endl;}intiIsprime(intiNum){ intiChushu; boolbFlag=false; for(iChushu=2;iChushu<=iNum-1;iChushu++) { if(iNum%iChushu==0) { bFlag=true; break; } } if(bFlag==false) return1; else return0;}第一次程式運(yùn)行結(jié)果為請(qǐng)輸入一個(gè)正整數(shù):3131是一個(gè)素?cái)?shù)第二次程式運(yùn)行結(jié)果為請(qǐng)輸入一個(gè)正整數(shù):119119不是一個(gè)素?cái)?shù)2.1.3函數(shù)的參數(shù)傳遞函數(shù)的參數(shù)用於在調(diào)用函數(shù)與被調(diào)用函數(shù)之間進(jìn)行數(shù)據(jù)傳遞。在函數(shù)定義時(shí),函數(shù)名後面括弧內(nèi)的參數(shù)稱(chēng)為形式參數(shù)(簡(jiǎn)稱(chēng)形參)。在函數(shù)被調(diào)用時(shí),函數(shù)名後面括弧內(nèi)的參數(shù)稱(chēng)為實(shí)際參數(shù)(簡(jiǎn)稱(chēng)實(shí)參)。

當(dāng)函數(shù)未被調(diào)用時(shí),C++編譯系統(tǒng)並沒(méi)有給函數(shù)的形參分配相應(yīng)的記憶體空間,函數(shù)的形參更不會(huì)有實(shí)際的值。只有在函數(shù)被調(diào)用時(shí),C++編譯系統(tǒng)這時(shí)才為形參分配實(shí)際的存儲(chǔ)單元,並將實(shí)參與形參結(jié)合。實(shí)參可以是常量、變數(shù)或運(yùn)算式,其類(lèi)型必須與形參相符。函數(shù)的參數(shù)傳遞,指的就是形參與實(shí)參結(jié)合(簡(jiǎn)稱(chēng)形實(shí)結(jié)合)的過(guò)程。形實(shí)結(jié)合的方式有值調(diào)用和引用調(diào)用兩種。1.值調(diào)用值調(diào)用是指當(dāng)發(fā)生函數(shù)調(diào)用時(shí),編譯系統(tǒng)為形參分配相應(yīng)的存儲(chǔ)空間並且直接將實(shí)參的值複製給形參,這樣形參和實(shí)參就各自擁有不同的存儲(chǔ)單元,且形參是實(shí)參的副本。因此,值調(diào)用過(guò)程是參數(shù)值的單向傳遞過(guò)程,一旦形參獲得了與實(shí)參相同的值就與實(shí)參脫離關(guān)係,以後不論形參發(fā)生多大的改變,都決不會(huì)反過(guò)來(lái)影響到實(shí)參。前面2.1.2節(jié)中的四道例題均屬於值調(diào)用方式。【例2-5】從鍵盤(pán)輸入兩個(gè)整數(shù),交換位置後輸出(交換未成功)。#include<iostream.h>voidswap(inta,intb);voidmain(){ intx,y; x=5; y=10; cout<<"x="<<x<<"y="<<y<<endl; swap(x,y);//交換x,y的值cout<<"afterswap"<<endl; cout<<"x="<<x<<"y="<<y<<endl;}voidswap(inta,intb){ intt; t=a; a=b; b=t;}

程式運(yùn)行結(jié)果為

x=5y=10afterswapx=5y=10

分析:從上面的程式運(yùn)行結(jié)果可以看出,並沒(méi)有達(dá)到交換的目的。這是因?yàn)閽?cǎi)用的傳遞方式不合乎問(wèn)題的要求。在單向值傳遞方式中,形參值雖確實(shí)進(jìn)行了交換,但這些改變對(duì)實(shí)參不起任何作用。

執(zhí)行主調(diào)函數(shù)中的函數(shù)調(diào)用語(yǔ)句swap(x、y)後,編譯系統(tǒng)將實(shí)參x中的值5傳遞給虛參a,將實(shí)參y中的值10傳遞給虛參b;在swap函數(shù)中,a、b中的值完成互換;返回主函數(shù)時(shí),實(shí)參x、y中的值不受虛參a、b的影響,並未進(jìn)行交換。2.引用調(diào)用顯而易見(jiàn),值調(diào)用時(shí)參數(shù)的傳遞方式是實(shí)參單向複製其值給虛參,如果我們想使子函數(shù)中對(duì)形參所做的任何更改也能及時(shí)反映給主函數(shù)中的實(shí)參(即希望形參與實(shí)參的影響是互相的或稱(chēng)是雙向的),又該怎麼辦呢?這就需要改變調(diào)用方式,即採(cǎi)用第二種參數(shù)傳遞方式——引用調(diào)用。引用是一種特殊類(lèi)型的變數(shù),可以被認(rèn)為是某一個(gè)變數(shù)的別名。通過(guò)引用名與通過(guò)被引用的變數(shù)名訪問(wèn)變數(shù)的效果是一樣的。這就是說(shuō),對(duì)形參的任何操作也就直接作用於實(shí)參。

例如:

inta,b;int&ra=a; //建立一個(gè)int型的引用ra,並將其初始化為變數(shù)a的一個(gè)別名

b=10;ri=b; //相當(dāng)於a=b;

注意:①聲明一個(gè)引用時(shí),必須同時(shí)對(duì)它進(jìn)行初始化,使它與一個(gè)已存在的對(duì)象關(guān)聯(lián)。②一旦一個(gè)引用被初始化後,就不能改變關(guān)聯(lián)對(duì)象。換言之,一個(gè)引用從它被聲明之後,就必須確定是哪個(gè)變數(shù)的別名,而且自始至終只能作為這一個(gè)變數(shù)的別名,不能另作他用。形參也可以引用的方式出現(xiàn)在形參表中。引用作為形參的情況與變數(shù)的引用稍有不同。這是因?yàn)?,形參的初始化不在?lèi)型說(shuō)明時(shí)進(jìn)行,而是在執(zhí)行主調(diào)函數(shù)中的調(diào)用語(yǔ)句時(shí),才為形參分配記憶體空間,同時(shí)用實(shí)參來(lái)初始化形參。【例2-6】使用引用調(diào)用改寫(xiě)例2-5的程式,使兩實(shí)參中的數(shù)真正進(jìn)行互換。#include<iostream.h>voidswap(int&a,int&b);voidmain(){ intx,y; x=5; y=10; cout<<"x="<<x<<"y="<<y<<endl; swap(x,y);//交換x,y的值

cout<<"afterswap"<<endl; cout<<"x="<<x<<"y="<<y<<endl;}voidswap(int&a,int&b){ intt; t=a; a=b; b=t;}程式運(yùn)行結(jié)果為x=5y=10afterswapx=10y=5

分析:子函數(shù)swap的兩個(gè)參數(shù)都是引用,當(dāng)被調(diào)用時(shí),它們分別被初始化成為a和b的別名。因此,在子函數(shù)swap中將兩個(gè)參數(shù)的值進(jìn)行交換後,交換結(jié)果可以返回主函數(shù)main。2.2函數(shù)調(diào)用機(jī)制

一個(gè)C++的根源程式經(jīng)過(guò)編譯以後形成與根源程式主名相同但尾碼為.exe的可執(zhí)行檔,且存放在外存儲(chǔ)器中。當(dāng)該.exe的可執(zhí)行程式被運(yùn)行時(shí),首先從外存將程式代碼裝載到記憶體的代碼區(qū),然後從main函數(shù)的起始處開(kāi)始執(zhí)行。程式在執(zhí)行過(guò)程中,如果遇到了對(duì)其他函數(shù)的調(diào)用,則暫停當(dāng)前函數(shù)的執(zhí)行,

保存下一條指令的地址(即返回地址,作為從子函數(shù)返回後繼續(xù)執(zhí)行的入口點(diǎn)),並保存現(xiàn)場(chǎng)(主要是一些寄存器的內(nèi)容),然後轉(zhuǎn)到子函數(shù)的入口地址,執(zhí)行子函數(shù)。當(dāng)遇到return語(yǔ)句或者子函數(shù)結(jié)束時(shí),則恢復(fù)先前保存的現(xiàn)場(chǎng),並從先前保存的返回地址開(kāi)始繼續(xù)執(zhí)行。圖2-1說(shuō)明了函數(shù)調(diào)用和返回的過(guò)程,圖中標(biāo)號(hào)標(biāo)明了執(zhí)行順序。圖2-1函數(shù)調(diào)用和返回的示意圖【例2-7】求

設(shè)N=10,X=2、4、6、8,即求N事件中每次取2、4、6、8的組合數(shù)。分析:這個(gè)問(wèn)題需要反復(fù)利用兩個(gè)公式:①N!②N!/X!/(N-X)!

設(shè)計(jì)兩個(gè)函數(shù):一個(gè)求整數(shù)階乘的函數(shù)lJiecheng和一個(gè)求組合數(shù)的函數(shù)lComb。由主函數(shù)main調(diào)用lComb,lComb又調(diào)用lJiecheng。程式代碼如下:#include<iostream.h>longlJiecheng(intn){ longrt=1; inti; for(i=1;i<=n;i++) rt=rt*i; returnrt;}longlComb(intN,intX){ returnlJiecheng(N)/lJiecheng(X)/lJiecheng(N-X);}voidmain(){ longlJiecheng(intn); longlComb(intN,intX); intiNum,x; do {cout<<"請(qǐng)輸入事件數(shù)(大於等於8):"; cin>>iNum; }while(iNum<10); for(x=2;x<10;x+=2) cout<<"C("<<iNum<<","<<x<<")="<<lComb(iNum,x)<<endl;}程式運(yùn)行結(jié)果為請(qǐng)輸入事件數(shù)(大於等於8):11C(11,2)=55C(11,4)=330C(11,6)=462C(11,8)=1652.3遞歸函數(shù)

遞歸函數(shù)又稱(chēng)為自調(diào)用函數(shù),其特點(diǎn)是,在函數(shù)內(nèi)部直接或間接地自己調(diào)用自己。所謂直接調(diào)用自身,就是指在一個(gè)函數(shù)的函數(shù)體中出現(xiàn)了對(duì)自身的調(diào)用語(yǔ)句。例如:

voidfunc1(void){...func1(); //func1調(diào)用func1自身

...}

所謂間接調(diào)用自身,就是一個(gè)函數(shù)func1調(diào)用另一個(gè)函數(shù)func2,而函數(shù)func2中又調(diào)用了函數(shù)func1,於是構(gòu)成間接遞歸。下麵的例子屬於間接調(diào)用情況。

voidfunc1(void){...func2(); //func1調(diào)用func2...}voidfunc2(void){...func1(); //func2調(diào)用func1...}func1函數(shù)就是通過(guò)func2實(shí)現(xiàn)間接遞歸。遞歸演算法的實(shí)質(zhì)是將原有的問(wèn)題分解為新的問(wèn)題,而解決新問(wèn)題時(shí)又用到了原有問(wèn)題的解法。按照這一原則分解下去,每次出現(xiàn)的新問(wèn)題都是原有問(wèn)題的簡(jiǎn)化的子集,而最終分解出來(lái)的問(wèn)題,是一個(gè)已知解的問(wèn)題。這便是有限的遞歸調(diào)用?!纠?-8】編寫(xiě)函數(shù),用遞歸的方法求n!的值。在主程序中實(shí)現(xiàn)任意輸入n值並輸出計(jì)算結(jié)果。分析:計(jì)算n!的公式如下。

1(n=0)n!=n(n-1)!(n>0)

這是一個(gè)遞歸形式的公式,在描述階乘演算法時(shí),又用到了階乘,只不過(guò)求階乘的數(shù)在逐次減1,因而編程時(shí)也自然採(cǎi)用遞歸演算法。遞歸的結(jié)束條件是n=0。程式代碼如下:#include<iostream.h>longjc(intn){ longrt; if(n<0) cout<<"Dataerror!"<<endl; elseif(n==0)rt=1; //遞歸的結(jié)束條件

elsert=n*jc(n-1); //以參數(shù)減1的方式繼續(xù)遞歸

returnrt;}voidmain(){ longjc(intn); intn; longresult; do { cout<<"輸入一個(gè)正整數(shù):"; cin>>n; }while(n<=0);result=jc(n); //首次調(diào)用處

cout<<n<<"!="<<result<<endl;}

程式運(yùn)行結(jié)果為輸入一個(gè)正整數(shù):66!=720【例2-9】有5個(gè)人坐在一起,問(wèn)第1個(gè)人多少歲,他說(shuō)比第2個(gè)人大2歲。問(wèn)第2個(gè)人多少歲,他說(shuō)比第3個(gè)人大2歲。問(wèn)第3個(gè)人多少歲,他說(shuō)比第4個(gè)人大2歲。問(wèn)第4個(gè)人多少歲,他說(shuō)比第5個(gè)人大2歲。最後問(wèn)第5個(gè)人,他說(shuō)是12歲。請(qǐng)問(wèn)第1個(gè)人多少歲?分析:這是一個(gè)遞歸問(wèn)題。每一個(gè)人的年齡都比其後那個(gè)人的年齡大2,即age(1)=age(2)+2age(2)=age(3)+2age(3)=age(4)+2age(4)=age(5)+2age(5)=12可以用公式表示如下:12(n=5)age(n)=age(n+1)+2(n<5)程式代碼如下:#include<iostream.h>intage(intn){ intss; if(n==5)ss=12; elsess=age(n+1)+2; return(ss);}voidmain(){ intage(intn); cout<<"第一個(gè)人的年齡為"<<age(1)<<"歲"<<endl;}程式運(yùn)行結(jié)果為第一個(gè)人的年齡為20歲2.4默認(rèn)參數(shù)的函數(shù)

在函數(shù)定義中通過(guò)賦值運(yùn)算就可指定默認(rèn)參數(shù)值。一旦程式在調(diào)用該函數(shù)時(shí),如果給出實(shí)參,則用實(shí)參初始化形參;如果沒(méi)有給出實(shí)參,則C++編譯系統(tǒng)自動(dòng)以預(yù)先賦值的默認(rèn)參數(shù)值作為傳入數(shù)值。一般情況下都將調(diào)用該函數(shù)時(shí)經(jīng)常用到的常數(shù)作為默認(rèn)參數(shù)值,這樣在調(diào)用時(shí)就無(wú)需每次都寫(xiě)出該值了。指定默認(rèn)參數(shù)值可以使函數(shù)的使用更為簡(jiǎn)單,同時(shí)也增強(qiáng)了函數(shù)的可重用性。【例2-10】帶默認(rèn)形參值的函數(shù)例題。#include<iostream.h>intmult(intn,intk=2) //第二個(gè)形參具有默認(rèn)值{ if(k==2) return(n*n); else return(mult(n,k-1)*n);}voidmain(){ cout<<endl<<mult(5)<<endl; /*形參n用實(shí)參來(lái)初始化為5,形參k採(cǎi)用默認(rèn)值2,實(shí)現(xiàn)5*5*/ cout<<mult(5,3)<<endl; /*用實(shí)參來(lái)初始化形參,n為5,k為3,實(shí)現(xiàn)5*5*5*/}程式運(yùn)行結(jié)果為25125

默認(rèn)形參值必須按從右向左的順序定義。在有默認(rèn)值的形參右面,不能出現(xiàn)無(wú)默認(rèn)值的形參。因?yàn)樵谡{(diào)用時(shí),實(shí)參初始化形參是按從左向右的順序。例如:voidtry(intj=3,intk) //非法voidtry(intj,intk=2,intm) //非法voidtry(intj,intk=7) //合法voidtry(intj,intk=2,intm=3) //合法voidtry(intj=3,intk=2,intm=3) //合法默認(rèn)形參值應(yīng)該在函數(shù)原型中給出。例如:intmulti(intx=2,inty=5); //默認(rèn)形參值在函數(shù)原型中給出voidmain(){multi(); //並非無(wú)參調(diào)用,而是採(cǎi)用默認(rèn)值,x取值2,y取值5}intmulti(intx,inty){return(x*y);}

在相同的作用域內(nèi),默認(rèn)形參值的說(shuō)明應(yīng)保持唯一。但如果在不同的作用域內(nèi),允許說(shuō)明不同的默認(rèn)形參。這裏的作用域是指直接包含著函數(shù)原型說(shuō)明的大括弧所界定的範(fàn)圍。對(duì)作用域概念的詳細(xì)介紹請(qǐng)參閱第5章。例如:

intadd(intx=2,inty=5); //全局默認(rèn)形參值

voidmain(){intadd(intx=1,inty=9); //局部默認(rèn)形參值add();//此處調(diào)用時(shí),採(cǎi)用局部默認(rèn)形參值,x取值1,y取值9}voidfunc(void){add()//此處調(diào)用時(shí),採(cǎi)用全局默認(rèn)形參值,x取值2,y取值5}2.5內(nèi)聯(lián)函數(shù)

內(nèi)聯(lián)函數(shù)(也稱(chēng)線上函數(shù))是在C++中為提高程式運(yùn)行效率而引入的。所有函數(shù)調(diào)用時(shí)都會(huì)產(chǎn)生一些額外的開(kāi)銷(xiāo),主要是系統(tǒng)棧的保護(hù)、代碼的傳遞、系統(tǒng)棧的恢復(fù)以及參數(shù)傳遞等。對(duì)於一些函數(shù)體很小但又經(jīng)常使用的函數(shù),由於被調(diào)用的頻率非常高,這種額外開(kāi)銷(xiāo)也就很可觀,有時(shí)甚至?xí)?duì)運(yùn)行效率產(chǎn)生本質(zhì)的影響。

使用內(nèi)聯(lián)函數(shù)正是解決這一問(wèn)題的手段。內(nèi)聯(lián)函數(shù)不是在調(diào)用時(shí)發(fā)生轉(zhuǎn)移,而是在編譯時(shí)將函數(shù)體嵌入在每一個(gè)調(diào)用語(yǔ)句處。這樣就相對(duì)節(jié)省了參數(shù)傳遞、系統(tǒng)棧的保護(hù)與恢復(fù)等的開(kāi)銷(xiāo)。內(nèi)聯(lián)函數(shù)在定義時(shí)使用關(guān)鍵字inline區(qū)別於一般函數(shù),其語(yǔ)法形式如下:

<inline><類(lèi)型識(shí)別字><被調(diào)函數(shù)名>(含類(lèi)型說(shuō)明的形參表){

函數(shù)體

}

例如:

inlineintmul(inta,intb){returna*b;

}

當(dāng)程式中出現(xiàn)mul(2+3,4)的函數(shù)調(diào)用時(shí),編譯程序就會(huì)將其擴(kuò)展為(2+3)*4。關(guān)鍵字inline是一個(gè)編譯命令,編譯程序在遇到這個(gè)命令時(shí)將記錄下來(lái),在處理內(nèi)聯(lián)函數(shù)的調(diào)用時(shí),編譯程序就試圖產(chǎn)生擴(kuò)展碼。這樣從使用者的角度來(lái)看,內(nèi)聯(lián)函數(shù)在語(yǔ)法上與一般函數(shù)沒(méi)有什麼區(qū)別,只是在編譯程式生成目標(biāo)代碼時(shí)才區(qū)別處理。

注意:①內(nèi)聯(lián)函數(shù)體內(nèi)一般不能有迴圈語(yǔ)句和switch語(yǔ)句。②內(nèi)聯(lián)函數(shù)的定義必須出現(xiàn)在第一次被調(diào)用之前。③對(duì)內(nèi)聯(lián)函數(shù)不能進(jìn)行異常介面聲明。如果違背了上述注意事項(xiàng)中的任一項(xiàng),編譯程序就會(huì)無(wú)視關(guān)鍵字inline的存在,像處理一般函數(shù)一樣處理,不生成擴(kuò)展代碼。因此,只有很簡(jiǎn)單而使用頻率很高的函數(shù)才被說(shuō)明為內(nèi)聯(lián)函數(shù)。內(nèi)聯(lián)函數(shù)會(huì)擴(kuò)大目標(biāo)代碼,使用時(shí)要謹(jǐn)慎?!纠?-11】?jī)?nèi)聯(lián)函數(shù)例題。#include<iostream.h>#include<iomanip.h>inlineintmax(inta,intb){ if(a>b) returna; else returnb;}voidmain(){ inta,b,c,d; a=210; b=150; c=20; d=max(a,b); d=max(d,c); //編譯時(shí)兩個(gè)調(diào)用處均被替換為max函數(shù)體語(yǔ)句。

cout<<"Thebiggestof" <<setw(5)<<a <<setw(5)<<b<<setw(5)<<c<<"is"<<d<<endl;}程式運(yùn)行結(jié)果為T(mén)hebiggestof21015020is2102.6函數(shù)重載

函數(shù)的重載也稱(chēng)多態(tài)函數(shù)。C++編譯系統(tǒng)允許為兩個(gè)或兩個(gè)以上的函數(shù)取相同的函數(shù)名,但是形參的個(gè)數(shù)或者形參的類(lèi)型不應(yīng)相同,編譯系統(tǒng)會(huì)根據(jù)實(shí)參和形參的類(lèi)型及個(gè)數(shù)的最佳匹配,自動(dòng)確定調(diào)用哪一個(gè)函數(shù),這就是所謂的函數(shù)重載。

對(duì)於沒(méi)有重載機(jī)制的C語(yǔ)言,每個(gè)函數(shù)必須有其不同於其他函數(shù)的名稱(chēng),即使操作是相同的,僅僅數(shù)據(jù)的類(lèi)型不相同,也需要定義名稱(chēng)完全不同的函數(shù),這樣就顯得重複且效率低下。例如,定義求平方函數(shù),就必須對(duì)整數(shù)的平方、浮點(diǎn)數(shù)的平方以及雙精度數(shù)的平方分別用不同的函數(shù)名:

intisq(intx,inty);floatfsq(floatx,floaty);doubledsq(doublex,doubley);

程式在調(diào)用這三個(gè)不同類(lèi)型的函數(shù)時(shí),是以名字加以區(qū)別的,需要記住並區(qū)別它們的名稱(chēng)。顯然,這樣就造成了代碼的重複,使用起來(lái)也不方便,更不利於代碼的維護(hù)。對(duì)於具有重載機(jī)制的C++語(yǔ)言,允許功能相近的函數(shù)在相同的作用域內(nèi)以相同函數(shù)名定義,因而使函數(shù)方便使用,便於記憶,也使程式設(shè)計(jì)更加靈活。仍以上例而言,在C++中只要用一個(gè)函數(shù)名即可,如square(),然後以賦給此函數(shù)的參數(shù)類(lèi)型來(lái)決定是要計(jì)算int型、float型,還是double型的數(shù)的平方。上例在C++中的定義形式如下:intsquare(intx);

floatsquare(floatx);

doublesquare(doublex);要計(jì)算square(3)時(shí),C++自動(dòng)使用第一種形式;計(jì)算square(3.25)時(shí),C++自動(dòng)使用第三種形式;計(jì)算square(3.25f)時(shí),C++自動(dòng)使用第二種形式。但是決不可以定義兩個(gè)具有相同名稱(chēng)、相同參數(shù)類(lèi)型和相同參數(shù)個(gè)數(shù),只是函數(shù)返回值不同的重載函數(shù)。

例如,以下定義是C++不允許的:

intfunc(intx);

floatfunc(intx);由此可見(jiàn),C++是按函數(shù)的參數(shù)表分辨相同名稱(chēng)的函數(shù)。如果參數(shù)表相同,則認(rèn)為是錯(cuò)誤的說(shuō)明。

C++允許重載函數(shù)有數(shù)量不同的參數(shù)個(gè)數(shù)。當(dāng)函數(shù)名相同而參數(shù)個(gè)數(shù)不同時(shí),C++會(huì)自動(dòng)按參數(shù)個(gè)數(shù)定向到正確的要調(diào)用的函數(shù)。下例說(shuō)明了C++的這一特性。

【例2-12】重載函數(shù)應(yīng)用例題。#include<iostream.h>intadd(intx,inty){ intsum; sum=x+y; return(sum);}intadd(intx,inty,intz){intsum; sum=x+y+z; return(sum);}voidmain(){ inta,b; a=add(5,10); b=add(5,10,20); cout<<"a="<<a<<"b="<<b<<endl;}程式運(yùn)行結(jié)果為a=15b=352.7函數(shù)模板

有很多時(shí)候,我們希望所設(shè)計(jì)的演算法可以處理多種數(shù)據(jù)類(lèi)型。但是,即使這一演算法被設(shè)計(jì)為重載函數(shù),也只是使用相同的函數(shù)名,函數(shù)體仍然要分別定義。如下面兩個(gè)求較小值的函數(shù):

intsmall(intx,inty){returnx<y?x:y;

}doublesmall(doublex,doubley){returnx<y?x:y;

}

考察以上兩個(gè)函數(shù),有如下特點(diǎn):只有參數(shù)類(lèi)型不同,返回值類(lèi)型不同,功能則完全一樣。類(lèi)似這樣的情況,可以使用函數(shù)範(fàn)本,從而避免函數(shù)體的重複定義。

函數(shù)範(fàn)本可以用來(lái)創(chuàng)建一個(gè)通用功能的函數(shù),以支持多種不同形參,簡(jiǎn)化重載函數(shù)的函數(shù)體設(shè)計(jì)。它的最大特點(diǎn)是把函數(shù)所使用的數(shù)據(jù)類(lèi)型作為參數(shù)。函數(shù)範(fàn)本的定義形式如下:

<template><typename識(shí)別字>

函數(shù)定義

【例2-13】定義一個(gè)能交換兩個(gè)變數(shù)值的函數(shù),要求用範(fàn)本函數(shù)實(shí)現(xiàn)。#include<iostream.h>template<typenameT>voidswap(T&x,T&y){ Tz; z=y;y=x;x=z;}voidmain(){ intm=1,n=8; doubleu=-5.5,v=99.3; cout<<"m="<<m<<"n="<<n<<endl; cout<<"u="<<u<<"v="<<v<<endl; swap(m,n); //整型

swap(u,v); //雙精度型

cout<<"m與n,u與v交換以後:"<<endl; cout<<"m="<<m<<"n="<<n<<endl; cout<<"u="<<u<<"v="<<v<<endl;}

程式運(yùn)行結(jié)果為

m=1n=8u=-5.5v=99.3m與n,u與v交換以後:

m=8n=1u=99.3v=-5.5

分析:編譯系統(tǒng)從調(diào)用swap()時(shí),根據(jù)實(shí)參的類(lèi)型推導(dǎo)出函數(shù)範(fàn)本的類(lèi)型參數(shù)。

於調(diào)用swap(m,n),由於實(shí)參m及n為int類(lèi)型,所以,推導(dǎo)出範(fàn)本中類(lèi)型參數(shù)T為int。當(dāng)類(lèi)型參數(shù)的含義確定後,編譯器將以函數(shù)範(fàn)本為樣板生成一個(gè)函數(shù):

intswap(int&x,int&y){intz;

z=y;y=x;x=z;

}

同樣,對(duì)於調(diào)用swap(u,v),由於實(shí)參u、v為double類(lèi)型,所以,推導(dǎo)出範(fàn)本中類(lèi)型參數(shù)T為double。

接著,編譯器將以函數(shù)範(fàn)本為樣板,生成如下函數(shù):

doubleswap(double&x,double&y){doublez;

z=y;y=x;x=z;

}

因此,當(dāng)主函數(shù)第一次調(diào)用swap()時(shí),執(zhí)行的實(shí)際上是由函數(shù)範(fàn)本生成的函數(shù):intswap(int&x,int&y)當(dāng)主函數(shù)第二次調(diào)用swap()時(shí),執(zhí)行的實(shí)際上是由函數(shù)範(fàn)本生成的函數(shù):doubleswap(double&x,double&y)2.8使用C++系統(tǒng)函數(shù)C++不僅允許我們根據(jù)需要自定義函數(shù),而且C++的系統(tǒng)庫(kù)中還提供了幾百個(gè)常用函數(shù)可供程式員使用。如求平方根函數(shù)(sqrt)、求浮點(diǎn)數(shù)或雙精度數(shù)的絕對(duì)值函數(shù)(fabs)、對(duì)數(shù)函數(shù)(log)、指數(shù)函數(shù)(exp)、三角函數(shù)等都屬於數(shù)學(xué)函數(shù)。輸入/輸出格式控制函數(shù)有setw()、setprecision()等。

由前面已學(xué)習(xí)的知識(shí)可知,調(diào)用函數(shù)之前必須先聲明函數(shù)原型。系統(tǒng)函數(shù)的原型聲明已經(jīng)全部由系統(tǒng)提供了,並且已分類(lèi)存在於不同的頭檔中。程式員需要做的事情,就是用include指令嵌入相應(yīng)的頭檔,然後便可以使用系統(tǒng)函數(shù)了。例如,要使用基本輸入/輸出流函數(shù)cin()/cout()函數(shù),就必須嵌入頭檔iostream.h。

若要使用數(shù)學(xué)函數(shù),如求絕對(duì)值函數(shù)abs()、fabs(),三角函數(shù)sin()、cos()、tan(),開(kāi)平方函數(shù)sqrt(),對(duì)數(shù)值函數(shù)log(),以e為底的指數(shù)函數(shù)exp(),就要嵌入頭檔math.h。同樣,要使用輸入/輸出格式控制函數(shù)setw()/setprecision(),就要嵌入頭檔iomanip.h。【例2-14】系統(tǒng)函數(shù)應(yīng)用例題。從鍵盤(pán)輸入一個(gè)角度值,求出該角度的正弦值、余弦值和正切值。

分析:系統(tǒng)函數(shù)中提供了求正弦值、余弦值和正切值的函數(shù)——sin()、cos()及tan()函數(shù)的說(shuō)明在頭檔math.h中。同樣,系統(tǒng)函數(shù)中也提供了輸入/輸出格式控制函數(shù),如輸出域?qū)捒刂坪瘮?shù)setw()、輸出精度控制函數(shù)setprecision(),函數(shù)的說(shuō)明在頭檔iomanip.h中。因此,需要用到這些系統(tǒng)函數(shù)時(shí),就必須將該函數(shù)所屬的頭檔以#include<頭檔案名>或#include“頭檔案名”的形式寫(xiě)在程式代碼開(kāi)始部分。程式代碼如下:#include<iostream.h>#include<math.h>#include<iomanip.h>constdoublepi=3.14159265;voidmain(){ doublea,b; cin>>a; b=a*pi/180;cout<<"sin("<<a<<")="<<setw(10)<<sin(b)<<endl; cout<<"cos("<<a<<")="<<setw(10)<<cos(b)<<endl; cout<<"tan("<<a<<")="<<setw(10)<<tan(b)<<endl;}程式運(yùn)行結(jié)果為輸入:30sin(30)=0.5cos(30)=0.866025tan(30)=0.57735

充分利用系統(tǒng)函數(shù),可以大大減少編程的工作量,提高程式的運(yùn)行效率和可靠性。要使用系統(tǒng)函數(shù),應(yīng)該注意以下兩點(diǎn):①瞭解所使用的C++開(kāi)發(fā)環(huán)境提供了哪些系統(tǒng)函數(shù)。不同的編譯系統(tǒng)提供的系統(tǒng)函數(shù)有所不同。②確定要使用的系統(tǒng)函數(shù)的聲明在哪個(gè)頭檔中。這也可以在庫(kù)函數(shù)參考手冊(cè)或聯(lián)機(jī)幫助中查到。

例如,在MSDNLibraryVisualStudio6.0中查找VC++6.0系統(tǒng)函數(shù)的分類(lèi)列表:首先在“活動(dòng)子集”欄選擇VisualC++Documentation,然後按如下路徑選擇:VisualC++Documentation→UsingVisualC++→VisualC++Programmer'sGuide→Run-TimeLibraryReference→Run-TimeRoutinesbyCategory→Run-TimeRoutinesbyCategory,如圖2-2。該幫助系統(tǒng)中將函數(shù)按如下分類(lèi)列出:獲取參數(shù)(Argumentaccess)浮點(diǎn)支持(Floating-pointsupport)緩衝區(qū)操作(Buffermanipulation)輸入與輸出(Inputandoutput)位元組分類(lèi)(Byteclassification)國(guó)際化(Internationalization)字元分類(lèi)(Characterclassification)記憶體分配(Memoryallocation)數(shù)據(jù)轉(zhuǎn)換(Dataconversion)處理機(jī)與環(huán)境控制(Processandenvironmentcontrol)調(diào)試(Debug)查找與排序(Searchingandsorting)目錄控制(Directorycontrol)字串操作(Stringmanipulation)錯(cuò)誤處理(Errorhandling)系統(tǒng)調(diào)用(Systemcalls)異常處理(Exceptionhandling)時(shí)間管理(Timemanagement)檔處理(Filehandling)圖2-2MSDNLibraryVisualStudio6.0窗口第3章數(shù)組3.1數(shù)組的基本概念3.2一維數(shù)組3.3多維數(shù)組3.4數(shù)組作為函數(shù)的參數(shù)3.5數(shù)組與字串3.6數(shù)組應(yīng)用舉例3.7構(gòu)造數(shù)據(jù)類(lèi)型3.1數(shù)組的基本概念

數(shù)組是一種構(gòu)造數(shù)據(jù)類(lèi)型,是具有統(tǒng)一名稱(chēng)和相同類(lèi)型的一組數(shù)據(jù)元素的集合,它佔(zhàn)用連續(xù)記憶體單元進(jìn)行存儲(chǔ)。要引用數(shù)組中的特定位置或元素,就要指定數(shù)組中的特定位置或元素的位置號(hào)(positionnumber)。

圖3-1顯示了整型數(shù)組c的數(shù)組元素存儲(chǔ)分配。這個(gè)數(shù)組包含7個(gè)元素??梢杂脭?shù)組名加上方括號(hào)([])中該元素的位置號(hào)來(lái)引用該元素。數(shù)組中的第一個(gè)元素稱(chēng)為第0個(gè)元素。這樣,c數(shù)組中的第一個(gè)元素為c[0],c數(shù)組中的第二個(gè)元素為c[1],…,c數(shù)組中的第七個(gè)元素為c[6]。一般來(lái)說(shuō),c數(shù)組中的第i個(gè)元素為c[i-1]。圖3-1整型數(shù)組c的數(shù)組元素存儲(chǔ)分配示意

方括號(hào)中的位置號(hào)通常稱(chēng)為下標(biāo)(subscript)。下標(biāo)應(yīng)為整數(shù)或整型運(yùn)算式。注意:帶下標(biāo)的數(shù)組名一般稱(chēng)為下標(biāo)變數(shù),可用於賦值語(yǔ)句的左邊。例如:

c[3]=72;3.2一維數(shù)組3.2.1一維數(shù)組的聲明數(shù)組在使用前必須先聲明。聲明一個(gè)一維數(shù)組的形式如下:

<類(lèi)型識(shí)別字><數(shù)組名>[數(shù)組長(zhǎng)度]其中:①數(shù)組名必須遵循C++語(yǔ)言對(duì)識(shí)別字的要求,其命名規(guī)則與其它變數(shù)名的相同。②數(shù)組長(zhǎng)度是個(gè)常量運(yùn)算式,它規(guī)定了數(shù)組的大小,即所聲明的數(shù)組由多少個(gè)數(shù)據(jù)類(lèi)型相同的存儲(chǔ)空間組成。

組成數(shù)組的對(duì)象稱(chēng)為該數(shù)組的元素。數(shù)組元素可存儲(chǔ)的數(shù)據(jù)類(lèi)型由聲明時(shí)指定的C++語(yǔ)言數(shù)據(jù)類(lèi)型決定。數(shù)組的聲明為以後使用數(shù)組分配了存儲(chǔ)空間,數(shù)組中每個(gè)元素在內(nèi)存中是依次排列的。例如,intScore[50];定義了名稱(chēng)為Score的一維數(shù)組,該數(shù)組有50個(gè)元素,是int類(lèi)型的。在聲明數(shù)組時(shí),要注意數(shù)組的長(zhǎng)度只能由常量運(yùn)算式來(lái)決定,不能是變數(shù)。即,數(shù)組的長(zhǎng)度必須是確定的。例如:

intnMonth;floatfSales[nMonth*12];是錯(cuò)誤的。這個(gè)聲明在編譯時(shí)編譯器會(huì)給出錯(cuò)誤資訊。3.2.2一維數(shù)組中的元素訪問(wèn)數(shù)組中的每個(gè)元素可以當(dāng)成普通的變數(shù)使用。訪問(wèn)一維數(shù)組元素的形式如下:

<數(shù)組名>[下標(biāo)]

下標(biāo)就是元素索引值,它代表了要被訪問(wèn)的數(shù)組元素在內(nèi)存中的相對(duì)位置。下標(biāo)值的允許範(fàn)圍從0開(kāi)始到數(shù)組長(zhǎng)度-1。下標(biāo)等於0代表要訪問(wèn)的元素在數(shù)組的第1個(gè)位置上,下標(biāo)等於1代表要訪問(wèn)的元素在數(shù)組的第2個(gè)位置上,依次類(lèi)推。

例如,聲明一個(gè)長(zhǎng)度為20的整型數(shù)組,並將數(shù)組中的各個(gè)元素按順序賦予從50到70以1遞增的數(shù),即賦予數(shù)組的第0個(gè)元素的值為50,賦予數(shù)組的第1個(gè)元素的值為51,依此類(lèi)推。寫(xiě)出相應(yīng)的程式段。注意,必須有一個(gè)值從0開(kāi)始,以1為增量,遞增到19的變數(shù)作為訪問(wèn)數(shù)組時(shí)的下標(biāo),這樣才能訪問(wèn)到數(shù)組中所有的元素。

用一個(gè)簡(jiǎn)單的for迴圈就可以做到這一點(diǎn),而迴圈控制變數(shù)就是最好的下標(biāo)值。要按順序給數(shù)組元素賦予從50到70的值,也就是讓每個(gè)數(shù)組元素的值等於其下標(biāo)值加上50,所以只要將迴圈控制變數(shù)加上50賦予相應(yīng)的數(shù)組元素即可。程式段代碼如下:

intnData[20];for(intnIndex=0;nIndex<20;nIndex++)nData[nIndex]=nIndex+50;【例3-1】生成一個(gè)長(zhǎng)度為10的連續(xù)偶數(shù)序列,該偶數(shù)序列從2開(kāi)始。要求將此序列保存在數(shù)組中,並輸出此數(shù)組的每個(gè)元素的值。分析:顯然,先要聲明一個(gè)長(zhǎng)度為10的數(shù)組。模仿上面的做法,可以用一個(gè)迴圈來(lái)解決對(duì)所有數(shù)組元素的訪問(wèn),關(guān)鍵在於生成數(shù)列。偶數(shù)列是個(gè)很簡(jiǎn)單的數(shù)列,如果從0開(kāi)始,則規(guī)律為:第i個(gè)數(shù)等於i*2(i=0,1,2,…);如果從2開(kāi)始,則規(guī)律為:第i個(gè)數(shù)等於i*2+2(i=0,1,2,…)。程式代碼如下:#include<iostream.h>voidmain(){ intnEven[10];//定義用於存放10個(gè)偶數(shù)的數(shù)組

intnIndex; for(nIndex=0;nIndex<10;nIndex++) nEven[nIndex]=nIndex*2+2; for(nIndex=0;nIndex<10;nIndex++) { cout<<nEven[nIndex]<<""; } cout<<endl;}程式運(yùn)行結(jié)果為2 4 6 8 10 12 14 16 18 203.2.3一維數(shù)組的初始化變數(shù)可以在聲明時(shí)賦初值,數(shù)組也可以在聲明時(shí)給所有或部分?jǐn)?shù)組元素賦初始值。要給一維數(shù)組元素賦初始值,有如下兩種形式。形式1:

<類(lèi)型識(shí)別字><數(shù)組名>[數(shù)組長(zhǎng)度]={第0個(gè)元素值,第1個(gè)元素值,…,第n-1個(gè)元素值}

形式2:

<類(lèi)型識(shí)別字><數(shù)組名>[]={第0個(gè)元素值,第1個(gè)元素值,…,第n個(gè)元素值}

第一種形式將聲明一個(gè)長(zhǎng)度為“數(shù)組長(zhǎng)度”的值的數(shù)組,然後將花括弧內(nèi)的值依次賦予數(shù)組的各個(gè)元素?;ɡɑ?nèi)只能是常量運(yùn)算式。如果花括弧中的常量運(yùn)算式的個(gè)數(shù)小於數(shù)組長(zhǎng)度,則剩餘的數(shù)組元素就不被賦予初始值;如果花括弧中的常量運(yùn)算式的個(gè)數(shù)大於數(shù)組長(zhǎng)度,則編譯器會(huì)給出錯(cuò)誤資訊。第二種形式將聲明一個(gè)長(zhǎng)度為n的數(shù)組,並將花括弧內(nèi)的n個(gè)值依次賦給數(shù)組的各個(gè)元素?!纠?-2】一個(gè)班級(jí)有20名學(xué)生,所有學(xué)生的英語(yǔ)考試成績(jī)保存在一個(gè)一維數(shù)組中。編寫(xiě)程式,求出該班學(xué)生的英語(yǔ)考試平均成績(jī),並統(tǒng)計(jì)考試成績(jī)?cè)?0分以上(包括90分)的學(xué)生人數(shù)和不及格的學(xué)生人數(shù)。分析:為了統(tǒng)計(jì)平均成績(jī),需要有個(gè)變數(shù)保存所有學(xué)生的成績(jī)總和。求總和的方法就是在對(duì)每個(gè)數(shù)組元素訪問(wèn)時(shí),將其值累加到這個(gè)變數(shù)中,然後由此變數(shù)除以學(xué)生人數(shù)即得平均成績(jī)。要統(tǒng)計(jì)考試成績(jī)90分以上的學(xué)生人數(shù)和不及格的學(xué)生人數(shù),

需要分別設(shè)置兩個(gè)變數(shù)。在對(duì)每個(gè)數(shù)組元素進(jìn)行訪問(wèn)時(shí),如果元素值大於等於90,就將保存考試成績(jī)?cè)?0分以上的學(xué)生人數(shù)的變數(shù)值加1;如果元素值小於60,就將保存考試成績(jī)不及格的學(xué)生人數(shù)的變數(shù)值加1。程式代碼如下:#include<iostream.h>voidmain(){ intnScore[20]={90,88,45,92,76,59,89,93,60,51,91,65,82,74,92,35,66,78,62,91}; //用數(shù)組初始化的方法將成績(jī)存於數(shù)組nScore中

intnUnPassedCount=0; //定義記錄不及格人數(shù)的變數(shù)

intnHighScoreCount=0;//定義記錄90分以上人數(shù)的變數(shù)

intnSum=0; //定義求和的變數(shù)for(intni=0;ni<20;ni++) { nSum+=nScore[ni]; if(nScore[ni]<60) nUnPassedCount++; if(nScore[ni]>=90) nHighScoreCount++; } cout<<"平均分?jǐn)?shù)為:"<<(float)nSum/20<<endl; //將總和除以20就是平均成績(jī)。注意這裏為了得到精確的結(jié)果,//使用了強(qiáng)制類(lèi)型轉(zhuǎn)換將nSum從int型轉(zhuǎn)換成float型

cout<<"90分以上人數(shù)為:"<<nHighScoreCount<<endl; cout<<"不及格人數(shù)為:"<<nUnPassedCount<<endl;}程式運(yùn)行結(jié)果為平均分?jǐn)?shù):73.9590分以上人數(shù)為:6不及格人數(shù)為:43.3多維數(shù)組3.3.1多維數(shù)組的聲明聲明一個(gè)多維數(shù)組的形式如下:

<類(lèi)型識(shí)別字><數(shù)組名>[長(zhǎng)度1][長(zhǎng)度2]…[長(zhǎng)度n]

同一維數(shù)組相同,多維數(shù)組的數(shù)組名必須遵循C++語(yǔ)言識(shí)別字的命名規(guī)則,常量運(yùn)算式中不能有任何變數(shù)出現(xiàn)。為了更直觀地介紹多維數(shù)組,下麵以二維數(shù)組為例。

聲明一個(gè)二維數(shù)組的形式如下:

<類(lèi)型識(shí)別字><數(shù)組名>[第1維長(zhǎng)度][第2維長(zhǎng)度]

例如,語(yǔ)句floatfMatrix[3][4]將聲明一個(gè)數(shù)組名為fMatix且第1維長(zhǎng)度為3、第2維長(zhǎng)度為4的二維數(shù)組。在二維數(shù)組中,第1維常常稱(chēng)為行,第2維常常稱(chēng)為列。這樣,一個(gè)二維數(shù)組就可同一個(gè)二維表格對(duì)應(yīng)起來(lái),如表3-1所示。

表3-1二維數(shù)組與表格

列行01230fMatrix[0][0]fMatrix[0][1]fMatrix[0][2]fMatrix[0][3]1fMatrix[1][0]fMatrix[1][1]fMatrix[1][2]fMatrix[1][3]2fMatrix[2][0]fMatrix[2][1]fMatrix[2][2]fMatrix[2][3]

可以這樣理解二維數(shù)組:如果只給出二維數(shù)組的第1維下標(biāo),以一維數(shù)組來(lái)看二維數(shù)組,則這樣的數(shù)組中每個(gè)元素所代表的是另一個(gè)一維數(shù)組。例如,fMatrix[0]代表由4個(gè)f1oat類(lèi)型的元素組成的另一個(gè)一維數(shù)組(數(shù)組名為fMatrix[0],元素為fMatrix[0][0]、fMatrix[0][1]、fMatrix[0][2]、fMatrix[0][3])。不難算出,fMatrix中共有3*4=12個(gè)fIoat型元素。這12個(gè)元素在內(nèi)存中其實(shí)也是按順序存放的:先存放fMatrix[0]的4個(gè)元素,緊接著存放fMatrix[1]的4個(gè)元素,最後存放fMatrix[2]的4個(gè)元素。3.3.2訪問(wèn)多維數(shù)組中的元素要訪問(wèn)多維數(shù)組中的元素,同樣需要指定要訪問(wèn)的元素的下標(biāo)。多維數(shù)組的元素有多個(gè)下標(biāo),其書(shū)寫(xiě)形式如下:

<數(shù)組名>[第1維下標(biāo)][第2維下標(biāo)]…[第n維下標(biāo)]

下標(biāo)的值也是從0開(kāi)始,不能超過(guò)該維的長(zhǎng)度減1。下標(biāo)的值可以是任意運(yùn)算式的值,只要其值在該下標(biāo)的有效範(fàn)圍內(nèi)即可。

要訪問(wèn)二維數(shù)組中的某個(gè)元素,必須給出該元素所在的行和列。例如,fMatrix[2][1]代表數(shù)組名為fMatrix的二維數(shù)組中位於第2(從0開(kāi)始)行、第1(從0開(kāi)始)列的元素。同一維數(shù)組一樣,二維數(shù)組的元素也可以當(dāng)成變數(shù)進(jìn)行賦值或參與各種運(yùn)算式的計(jì)算。3.3.3二維數(shù)組的初始化同一維數(shù)組一樣,二維數(shù)組也可以在聲明時(shí)賦初始值,其形式如下。形式1:

<類(lèi)型識(shí)別字><數(shù)組名>[第1維長(zhǎng)度][第2維長(zhǎng)度]={第0個(gè)第2維數(shù)據(jù)組},

{第1個(gè)第2維數(shù)據(jù)組},…,{第n-1個(gè)第2維數(shù)據(jù)組}}

其中,n等於第1維長(zhǎng)度。

形式2:

<類(lèi)型識(shí)別字><數(shù)組名>[第1維長(zhǎng)度][第2維長(zhǎng)度]={第0個(gè)元素值,第1個(gè)元素值,…,第m個(gè)元素值}

其中,m小於或等於第1維長(zhǎng)度乘以第2維長(zhǎng)度。在兩種形式中,如果花括弧中給出的元素個(gè)數(shù)少於實(shí)際的元素個(gè)數(shù),則剩餘的元素就不會(huì)被賦予初始值;如果花括弧中給出的元素個(gè)數(shù)大於實(shí)際的元素個(gè)數(shù),則編譯器會(huì)給出錯(cuò)誤資訊?!纠?-3】生成如下格式的方陣,將其存入二維數(shù)組中,並輸出這個(gè)二維數(shù)組所有元素的值。

12345109876111213141520191817162122232425

分析:注意到這個(gè)方陣的規(guī)律在於,偶數(shù)行中的元素按昇冪排列,奇數(shù)行中的元素按降序排列,只要逐行處理方陣中的元素,即可得到這種方陣。為了訪問(wèn)二維數(shù)組中的所有元素,應(yīng)使用二重嵌套迴圈。外層迴圈的迴圈控制變數(shù)作為當(dāng)前行,內(nèi)層迴圈的迴圈控制變數(shù)作為當(dāng)前列。在顯示這個(gè)二維數(shù)組時(shí),為了得到理想的顯示效果,要對(duì)不同的元素指定不同的顯示位置。程式代碼如下:#include<iostream.h>voidmain(){ intnRow; //控制行的變數(shù)

intnCol; //控制列的變數(shù)

intnMatrix[5][5]; //聲明二維數(shù)組

for(nRow=0;nRow<5;nRow++){ for(nCol=0;nCol<5;nCol++) { if(nRow%2==0) nMatrix[nRow][nCol]=nRow*5+nCol+1; else nMatrix[nRow][4-nCol]=nRow*5+nCol+1; } } for(nRow=0;nRow<5;nRow++) {for(nCol=0;nCol<5;nCol++) { cout<<nMatrix[nRow][nCol]; if(nMatrix[nRow][nCol]<10) //控制輸出1位數(shù)與2位數(shù)時(shí)的不同間隔

cout<<""; else cout<<""; } cout<<endl; //每輸出一行後換行

}}程式運(yùn)行結(jié)果為

1 23 4 510 9 8 7 611 12 13 14 1520 19 18 17 162122 23 24 253.4數(shù)組作為函數(shù)的參數(shù)

在C++語(yǔ)言中,將整個(gè)數(shù)組作為參數(shù)傳遞給函數(shù)要涉及到指針的概念。有關(guān)內(nèi)容將在本書(shū)的第6章進(jìn)一步討論,這裏只結(jié)合數(shù)組參數(shù)的傳遞過(guò)程做簡(jiǎn)單介紹。要將數(shù)組作為參數(shù)傳遞給函數(shù),可由不帶方括號(hào)的數(shù)組名進(jìn)行。例如,如果數(shù)組聲明如下:intnMatrix[20];則將數(shù)組傳遞給函數(shù),可用下列函數(shù)調(diào)用語(yǔ)句:myArray(nMatrix,20);要傳遞數(shù)組,大體上有以下兩種形式。形式1:<類(lèi)型識(shí)別字><函數(shù)名>(類(lèi)型識(shí)別字?jǐn)?shù)組名[],int長(zhǎng)度)形式2:<類(lèi)型識(shí)別字><函數(shù)名>(類(lèi)型識(shí)別字?jǐn)?shù)組名[長(zhǎng)度])

第一種形式適於處理不同長(zhǎng)度的數(shù)組,數(shù)組的實(shí)際長(zhǎng)度通過(guò)另一個(gè)參數(shù)傳遞給函數(shù);而第二種形式只可用於傳遞長(zhǎng)度固定的數(shù)組。不管哪一種形式,傳遞給函數(shù)的都不是數(shù)組本身,而是保存數(shù)組第0個(gè)元素的記憶體單元的地址(即存儲(chǔ)數(shù)組的起始地址)。通過(guò)傳遞數(shù)組的開(kāi)始地址,被調(diào)用函數(shù)可得到實(shí)際數(shù)組的準(zhǔn)確存放位置。因此,被調(diào)用函數(shù)在函數(shù)體中修改數(shù)組元素時(shí),實(shí)際上是修改原記憶體地址中的數(shù)組元素。

數(shù)組名的值實(shí)際上就是保存數(shù)組中第1個(gè)元素的記憶體地址的變數(shù),這樣的變數(shù)稱(chēng)為指針型變數(shù)。當(dāng)進(jìn)行數(shù)組傳遞時(shí),實(shí)際參數(shù)將此地址值傳遞給形式參數(shù),使形式參數(shù)同實(shí)際參數(shù)指向同一記憶體地址。這樣在函數(shù)中如果改變數(shù)組中某個(gè)元素的值,在函數(shù)外數(shù)組中該元素的值也發(fā)生改變。

儘管函數(shù)調(diào)用按地址傳遞整個(gè)數(shù)組,但各個(gè)數(shù)組元素和簡(jiǎn)單變數(shù)一樣是按值傳遞。這種簡(jiǎn)單的單個(gè)數(shù)據(jù)稱(chēng)為下標(biāo)變數(shù)或標(biāo)量(scalar)。要將數(shù)組元素傳遞給函數(shù),可用數(shù)組元素的下標(biāo)名作為函數(shù)調(diào)用中的參數(shù)。數(shù)組元素、數(shù)組名與作為函數(shù)形式參數(shù)的數(shù)組名的這種關(guān)係可用圖3-2來(lái)表示。

鑒於上述原因,必須考慮在函數(shù)體內(nèi)對(duì)作為形式參數(shù)傳遞而來(lái)的數(shù)組的操作。如果函數(shù)體內(nèi)所有對(duì)作為形式參數(shù)傳遞而來(lái)的數(shù)組的操作只有讀操作沒(méi)有寫(xiě)操作,則不會(huì)有任何問(wèn)題。但如果要改變數(shù)組元素的值,就必須考慮函數(shù)的調(diào)用者是否允許函數(shù)改變數(shù)組元素的值。如果不允許,在函數(shù)內(nèi)部必須將數(shù)組複製,所有的更改操作只能對(duì)複製品進(jìn)行。

【例3-4】某次歌唱比賽有5名選手參加,有6名評(píng)委分別為選手打分,得分如表3-2。

表3-2歌唱比賽記分表評(píng)委號(hào)

選手號(hào)12345619.319.209.009.409.359.2029.719.529.509.669.499.5738.898.809.109.258.909.0049.389.509.409.209.908.9059.308.849.409.459.108.89

規(guī)定的積分規(guī)則是:每位選手去掉一個(gè)最高分,再去掉一個(gè)最低分,然後取剩下的得分的平均分。編寫(xiě)程式計(jì)算各選手的成績(jī),並在窗口輸出選手號(hào)和成績(jī)。分析:由於二維數(shù)組同二維表格有對(duì)應(yīng)關(guān)係,可以用一個(gè)二維數(shù)組保存所有評(píng)委給所有選手評(píng)出的成績(jī)。這樣,數(shù)組下標(biāo)的第1維(行)代表的就是選手號(hào)——i,第2維(列)代表的是評(píng)委號(hào)——j。

溫馨提示

  • 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝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ù)覽,若沒(méi)有圖紙預(yù)覽就沒(méi)有圖紙。
  • 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)論