第三章 基本控制結(jié)構(gòu)程序設(shè)計(jì).ppt_第1頁
第三章 基本控制結(jié)構(gòu)程序設(shè)計(jì).ppt_第2頁
第三章 基本控制結(jié)構(gòu)程序設(shè)計(jì).ppt_第3頁
第三章 基本控制結(jié)構(gòu)程序設(shè)計(jì).ppt_第4頁
第三章 基本控制結(jié)構(gòu)程序設(shè)計(jì).ppt_第5頁
已閱讀5頁,還剩90頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

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

文檔簡介

1、第三章 基本控制結(jié)構(gòu)程序設(shè)計(jì),結(jié)構(gòu)化程序設(shè)計(jì)的特點(diǎn)是任何程序都可由三種基本結(jié)構(gòu)及其組合來描述。本章將介紹C+分支結(jié)構(gòu)和循環(huán)結(jié)構(gòu)的設(shè)計(jì)方法。還將介紹一些常用算法。,第三章 基本控制結(jié)構(gòu)程序設(shè)計(jì),31 分支結(jié)構(gòu)程序設(shè)計(jì),35 枚舉類型,34 常用算法的應(yīng)用實(shí)例,33 轉(zhuǎn)向語句,32 循環(huán)結(jié)構(gòu)程序設(shè)計(jì),36 輸入輸出文件簡介,3.1 分支結(jié)構(gòu)程序設(shè)計(jì),對(duì)程序的運(yùn)行流程進(jìn)行控制,主要通過執(zhí)行專門用來控制流程的語句來實(shí)現(xiàn)。流程控制語句也稱為過程化語句。分支語句是三種基本流程控制語句之一。C+提供以下三種分支語句:,if 語句 條件運(yùn)算符 “ ? : ” swith 語句,3.1 分支結(jié)構(gòu)程序設(shè)計(jì),3.1

2、.1 if語句,3.1.2 條件運(yùn)算符“?:”,3.2.1 swich語句,3.1.1 if 語句,if語句有兩種基本格式為: 1、if () ; 2、if () else;,if 語句,【例31】 輸入一個(gè)年份,判斷是否閏年。 算法分析:假定年份為year, 閏年的條件是 : year%4=0 ,ok,分析:讀入三個(gè)數(shù),先求出兩個(gè)數(shù)中較大者,再將該大數(shù)與第三個(gè)數(shù)比較,求出最大數(shù)。 #include void main() int a, b, c, max; coutabc; coutb) max=a; else max=b; if(cmax) cout “最大數(shù)為:”cendl; else

3、cout “最大數(shù)為:”maxendl; ,if 語句,【例32】 從鍵盤上輸入三個(gè)整數(shù),輸出其中的最大數(shù)。,ok,if 語句中,如果內(nèi)嵌語句又是if語句,就構(gòu)成了嵌套if語句。if 語句可實(shí)現(xiàn)二選一分支,而嵌套if語句則可以實(shí)現(xiàn)多選一的多路分支情況。 嵌套有兩種形式,第一種是嵌套在else分支中: if () ; else if () 語句2; else if else ; 第二種是嵌套在if分支中為: if () if () ; else;,if 語句,/方法1:采用if中嵌套形式 #include void main() int a, b, c, max; coutabc; coutb)

4、 if(ac) max=a; /ab且ac else max=c; /ab且ac) max=b; /ac else max=c; /a=b且bc cout最大數(shù)max=max;,if 語句,【例3.3】用嵌套if語句完成【例3.2】的任務(wù)。,ok,/方法2:采用else中嵌套形式 #include void main() int a,b,c,max; coutabc; coutb ,if 語句,ok,要特別注意else和if的配對(duì)關(guān)系。C+規(guī)定了if和else的“就近配對(duì)”原則,即相距最近且還沒有配對(duì)的一對(duì)if和else首先配對(duì)。按上述規(guī)定,第二種嵌套形式中的else應(yīng)與第二個(gè)if配對(duì)。如果根

5、據(jù)程序的邏輯需要改變配對(duì)關(guān)系,則要將屬于同一層的語句放在一對(duì)“”中。如第二種嵌套形式中,要讓else和第一個(gè)if配對(duì),語句必須寫成: if (表達(dá)式1) if (表達(dá)式2) 語句1 ; else 語句2 ; 第二種嵌套形式較容易產(chǎn)生邏輯錯(cuò)誤,而第一種形式配對(duì)關(guān)系則非常明確,因此從程序可讀性角度出發(fā),建議盡量使用第一種嵌套形式。,請(qǐng)看以下兩個(gè)語句: /語句1: if(n%3=0) if(n%5=0) coutn是15的倍數(shù)endl; else cout n是3的倍數(shù)但不是5的倍數(shù) endl; /語句2: if(n%3=0) if(n%5=0) coutn是15的倍數(shù)endl; else cout

6、 n 不是3的倍數(shù) 兩個(gè)語句的差別只在于一個(gè)“”,但表達(dá)的邏輯關(guān)系卻完全不同。,【例34】 某商場(chǎng)優(yōu)惠活動(dòng)規(guī)定,某種商品單 價(jià)為80元,一次購買5件以上(包含 5件)10件以下(不包含10件)打9 折,一次購買10件以上(包含10件) 打8折。設(shè)計(jì)程序根據(jù)客戶的購買量計(jì) 算總價(jià)。,if 語句,算法,1、輸入購買件數(shù)count,設(shè)置單價(jià)price=80(元) 2、根據(jù)count值確定折扣discount; 3、實(shí)際售價(jià)amount=price*count*discount; 4、輸出amount的值。 算法細(xì)化: 2.1、if(count=5/單價(jià),折扣,總價(jià) int count;/購買件數(shù) c

7、outcount; if(count5) discount=1; else if(count10) discount=0.9; else discount=0.8; amount=price*count*discount; cout購買件數(shù):countendl; cout單價(jià):pricet折扣:“ discountendl; cout總價(jià):amountendl; 請(qǐng)?jiān)赩C+平臺(tái)上運(yùn)行,輸入不同的件數(shù),使程序所有分支都可以被執(zhí)行一次。,ok,【例35】 求一元二次方程 ax2+bx+c=0 的根。 其中系數(shù)a(a0)、b、c的值由鍵盤輸入。 分析:輸入系數(shù)a(a0)、b、c后,令delta= b

8、24ac,結(jié)果有三種情況: 若delta=0,方程有兩個(gè)相同實(shí)根; 若delta0,方程有兩個(gè)不同實(shí)根; 若delta0,方程無實(shí)根。,if 語句,算法,1、輸入系數(shù)a(a0)、b、c; 2、令delta= b24ac; 3、根據(jù)delta的值求方程的根; 4、輸出方程的根; 算法細(xì)化: 3.1、 if(delta=0)方程有兩個(gè)相同實(shí)根;計(jì)算 3.2、 if(delta0)方程有兩個(gè)不同實(shí)根;計(jì)算 3.3、 if(delta0)方程無實(shí)根;計(jì)算,ok,#include #include void main() float a,b,c; float delta,x1,x2; const flo

9、at zero=0.0001;/定義一個(gè)很小的常數(shù) coutabc; couta=atb=bt c=cendl; delta=b*b-4*a*c;,求一元二次方程的根源程序,if(fabs(delta)0) delta=sqrt(delta); x1=(-b+delta)/(2*a); x2=(-b-delta)/(2*a); cout方程有兩個(gè)不同實(shí)根:; coutx1=x1tx2=“ x2endl; else /delta0 cout方程無實(shí)根!endl; 請(qǐng)?jiān)赩C+平臺(tái)上運(yùn)行,輸入不同的系數(shù),使程序所有分支都可以被執(zhí)行一次。,3.1.2 條件運(yùn)算符“?:”,if語句在某些情況下可以用條件

10、運(yùn)算符“?:”來簡化表達(dá)?!?:”是一個(gè)三元運(yùn)算符,其構(gòu)成的表達(dá)式格式為: ? : 執(zhí)行邏輯:先計(jì)算表達(dá)式1,若其值為真(或非0),則計(jì)算表達(dá)式2(不計(jì)算表達(dá)式3),并將該值作為整個(gè)表達(dá)式的值;反之,即表達(dá)式1的值為假或?yàn)?,則計(jì)算表達(dá)式3(不計(jì)算表達(dá)式2),并將該值作為整個(gè)表達(dá)式的值。 例如:int a=6,b=7, min=ab?a:b; /min=6 min=ab?+a:+b; /min=7 a=7 b=7 min=ab?a+:b+; /min=6 a=7 b=7,ok,3.1.3 switch語句,用嵌套if語句可以實(shí)現(xiàn)多選一的情況。另外C+中還提供了一個(gè)switch語句,稱為開關(guān)語句

11、,也可以用來實(shí)現(xiàn)多選一: switch (表達(dá)式) case 常量表達(dá)式: 語句序列break; case 常量表達(dá)式n:語句序列nbreak; default:語句序列 ,switch語句格式,(1)各個(gè)case(包括default)分支出現(xiàn)的次序可以任意,通常將default放在最后。 (2)break語句可選,如果沒有break語句,每一個(gè)case分支都只作為開關(guān)語句的執(zhí)行入口,執(zhí)行完該分支后,還將接著執(zhí)行其后的所有分支。因此,為保證邏輯的正確實(shí)現(xiàn),通常每個(gè)case 分支都與break語句聯(lián)用。 (3)每個(gè)常量表達(dá)式的取值必須各不相同,否則將引起歧義。,(4)允許多個(gè)常量表達(dá)式對(duì)應(yīng)同一個(gè)

12、語句序列。 例如: char score; cinscore; switch (score) case A: case a: coutexcellent; break; case B: case b: coutgood; break; default: coutfair; (5)從形式上看,switch語句的可讀性比嵌套if語句好,但不是所有多選一的問題都可由開關(guān)語句完成,這是因?yàn)殚_關(guān)語句中限定了條件表達(dá)式的取值類型。,ok,switch語句例子,【例36】 運(yùn)輸公司對(duì)所運(yùn)貨物實(shí)行分段計(jì)費(fèi)。設(shè)運(yùn)輸里程為s,則運(yùn)費(fèi)打折情況如下: s250 不打折扣 250=s500 2%折扣 500=s1000

13、5%折扣 1000=s20008%折扣 2000=s300010%折扣 3000=s15%折扣 設(shè)每公里每噸的基本運(yùn)費(fèi)為p,貨物重量為w,折扣為d,則總運(yùn)費(fèi)f為:f=p*w*s*(1-d) 設(shè)計(jì)程序,當(dāng)輸入p、w和s后,計(jì)算運(yùn)費(fèi)f。,算法,1、輸入每噸運(yùn)費(fèi)p、貨物重量w、運(yùn)輸里程s; 2、根據(jù)運(yùn)輸里程s計(jì)算折扣d; 3、計(jì)算總運(yùn)費(fèi)f=p*w*s*(1-d); 4、輸出計(jì)算結(jié)果; 算法細(xì)化: 2、根據(jù)運(yùn)輸里程s計(jì)算折扣d 分析:如果用switch語句,必須使表達(dá)式符合語法要求,分析發(fā)現(xiàn),里程s的分段點(diǎn)均是250的倍數(shù),因此,將里程s除以250,取整數(shù)商,便得到若干整數(shù)值。,ok,switch(c

14、=s/250) case 0: d=0; break; case 1: d=0.02; break; case 2: case 3: d=0.05; break; case 4: case 5: case 6: case 7: d=0.08; break; case 8: case 9: case 10: case 11:d=0.1;break; default:d=0.15; ,s250 不打折扣 250=s500 2%折扣 500=s1000 5%折扣 1000=s2000 8%折扣 2000=s3000 10%折扣 3000=s 15%折扣,#include #include void

15、main( ) int c,s; float p,w,d,f; coutpws; c=s/250; switch(c) case 0: d=0; break; case 1: d=0.02; break; case 2: case 3: d=0.05; break; case 4: case 5: case 6: case 7: d=0.08; break; case 8:case9:case10:case11:d=0.1;break; default:d=0.15; f=p*w*s*(1-d); cout運(yùn)輸單價(jià)為pt重量為wt 里程為sendl; cout折扣為dendl; cout運(yùn)費(fèi)為

16、fendl; 請(qǐng)?jiān)赩C+平臺(tái)上運(yùn)行,輸入不同的里程,使程序所有分支都可以被執(zhí)行一次。,ok,【例37】 設(shè)計(jì)一個(gè)計(jì)算器程序,實(shí)現(xiàn)加、減、乘、除運(yùn)算。 分析:讀入兩個(gè)操作數(shù)和運(yùn)算符,根據(jù)運(yùn)算符完成相應(yīng)運(yùn)算。 #include void main( ) float num1,num2; char op; coutnum1opnum2; switch(op) case +: coutnum1opnum2=num1+num2endl; break; case -: coutnum1opnum2=num1-num2endl; break; case *: coutnum1opnum2=num1*num2

17、endl; break; case /: coutnum1opnum2=num1/num2endl; break; default : coutop是無效運(yùn)算符!; 常量表達(dá)式采用字符型,上機(jī)運(yùn)行一下。,循環(huán)控制語句是三種基本流程控制語句之一。C+提供以下三種循環(huán)語句:,while語句 do-while 語句 for語句,3.2 循環(huán)結(jié)構(gòu)程序設(shè)計(jì),循環(huán)結(jié)構(gòu)程序設(shè)計(jì),3.2.1 while語句,3.2.4 循環(huán)的嵌套,3.2.3 for語句,3.2.2 do-while 語句,3.2.1 while 語句,while語句也稱為當(dāng)循環(huán)。 語句格式為: while (表達(dá)式) 循環(huán)體語句;,圖3.1

18、 while語句的執(zhí)行流程圖,求表達(dá)式的值,表達(dá)式值為真?,是,否,執(zhí)行循環(huán)體語句,while 語句,【例38】 求1+2+3+4的值。,ok,N個(gè)連續(xù)整數(shù)相加算法 1、設(shè)置變量i用來放被加數(shù),變量sum用來放和值,并初始化; 2、從第一個(gè)數(shù)開始,依次將被加數(shù)賦給i,并進(jìn)行操作sumsum+i; 3、輸出sum; 細(xì)化算法2: while(還有被加數(shù)) i=當(dāng)前被加數(shù); sum+=i; i準(zhǔn)備接受下一個(gè)被加數(shù); ,源程序如下: #include void main( ) int i=1,sum=0;/循環(huán)初始條件 while(i=4) sum+=i; i+;/修改循環(huán)條件 coutsum=su

19、mendl; 在VC+平臺(tái)上運(yùn)行,試一試是否正確,ok,while 語句,注意: 在有循環(huán)語句的程序中,通常循環(huán)開始前對(duì)循環(huán)條件進(jìn)行初始化;而在循環(huán)體語句中要包含修改循環(huán)條件的語句,否則循環(huán)將不能終止而陷入死循環(huán)。 C+表達(dá)方式靈活,上例中的循環(huán)語句還可以寫成: while (i=n) sum+=i+; 或者 while (sum+=i+, i=n) ;/循環(huán)體為空語句 修改程序后在VC+平臺(tái)上運(yùn)行,看是否正確,3.2.2 do-while 語句,do-while語句稱為直到循環(huán), 格式為: do 循環(huán)體語句 while( 表達(dá)式 ),否,是,表達(dá)式的 值為真?,執(zhí)行循環(huán)體語句,求表達(dá)式的值,

20、圖3.2 do-while語句的執(zhí)行流程圖,do-while 語句,do/while語句和while語句的區(qū)別: 多數(shù)情況下可以互相替代。 區(qū)別是do/while語句至少執(zhí)行一次循環(huán)體后再判斷循環(huán)條件是否滿足; while語句先判斷條件是否滿足,然后才執(zhí)行循環(huán)體。,【例39】 用迭代法求a的平方根近似值。求平方根的迭代公式為: 要求前后兩個(gè)迭代根之差小于10- 5。,do-while 語句,迭代法求解:a是已知正數(shù),x 0是迭代初值,給x 0一個(gè)值,假定 x 0 = a/2;則用迭代公式依次計(jì)算: x1=(x0+a/x0)/2;x2=(x1+a/x1)/2; xk+1=(xk+a/xk)/2;

21、 當(dāng)|xk+1 xk|(是一個(gè)較小的正數(shù))時(shí),迭代終止,取xk+1的值為a的平方根近似值。,ok,1、輸入a(a0)及較小正數(shù)delta(也可用常變量); 2、x 0 = a/2; 用迭代公式算 x1=(x0+a/x0)/2; 3、while(|x1 x0|=delta) x 0 = x 1 ;/把最近的值給x 0 ; x1=(x0+a/x0)/2; /求xk+1時(shí)只需要知道xk的值,所以只需2個(gè)變量; 4、取x1的值為a的平方根近似值,輸出。 2、3步驟很適合用do/while語句實(shí)現(xiàn): x 1 = a/2; dox0=x1; x1=(x0+a/x0)/2; while(|x1 x0|=de

22、lta);,和迭代法對(duì)應(yīng)的程序算法是遞推算法:,回到題目,#include #include void main( ) float x0,x1,a; couta; if(a=1e-5); cout a的平方根為:x1endl; 在VC+平臺(tái)上運(yùn)行,輸入2,3,4,5試一試是否正確,回到題目,【例310】 輸入一段文本,統(tǒng)計(jì)文本的行數(shù)、單詞數(shù)及字符數(shù)。假定單詞之間以空格或跳格或換行符間隔,且文本開始沒有空行。 算法分析: 1、逐個(gè)讀入文本中的字符,直到讀到一個(gè)輸入結(jié)束符EOF為止。 2、如何算行數(shù)?行結(jié)束標(biāo)志為讀到字符n; 3、如何算單詞數(shù)?設(shè)一個(gè)變量isword,讀到字符時(shí)isword=1,讀

23、到間隔符時(shí)isword=0;如果讀到一個(gè)間隔符而此時(shí)isword值為1,則說明剛讀完一個(gè)單詞;(如果讀到一個(gè)字符而此時(shí)isword值為0,則說明剛開始讀一個(gè)單詞;) 4、如何算字符數(shù)?,do-while 語句,ok,算法,1、設(shè)置變量line、word、ch分別代表行數(shù)、單詞數(shù)、非分隔字符數(shù),并初始化;設(shè)置變量isword來輔助統(tǒng)計(jì)單詞數(shù); 2、do從鍵盤讀入一個(gè)字符c; if ( c=n) line+; if (是單詞開頭) word+; if (c不是分隔符) ch+; while (c!= EOF ); 3、輸出統(tǒng)計(jì)結(jié)果。,將下面的程序在VC+平臺(tái)上運(yùn)行,試一試是否正確,#include

24、 void main( ) char c; int line=0, word=0, ch=0; int isword=0; do c=cin.get(); if (ch= n) line+; /遇換行符行數(shù)+1 if (c!= ,3.2.3 for 語句,for循環(huán)語句的格式為: for ( ; ; ) ,ok,for語句、while語句、do/while語句實(shí)現(xiàn)相同的功能:1+2+3+4,int i=1,sum=0; /循環(huán)初始條件 while(i=4) sum+=i; i+; /修改循環(huán)條件 ,int i=1,sum=0; /循環(huán)初始條件 do sum+=i; i+;/修改循環(huán)條件 whi

25、le(i=4);,for( int i=1,sum=0; i=4; i+ ) sum+=i; /*習(xí)慣上:表達(dá)式1:循環(huán)初始條件;表達(dá)式2:循環(huán)終止條件;表達(dá)式3:修改循環(huán)條件*/,ok,for 語句的應(yīng)用,for語句的幾點(diǎn)說明: 1、是先判斷型的,同while語句; 2、使用更為靈活: 三個(gè)表達(dá)式可以是任意表達(dá)式,因此他們就可以實(shí)現(xiàn)循環(huán)初始化、計(jì)算、修改循環(huán)條件等任務(wù),而不一定非在循環(huán)體中進(jìn)行;,for 語句的應(yīng)用,【例311】 設(shè)計(jì)程序輸出Fibonacii數(shù)列的前20項(xiàng),要求每行輸出5個(gè)數(shù)據(jù)。 Fibonacii數(shù)列定義如下:,算法分析:除了第0項(xiàng)和第1項(xiàng)外,每一項(xiàng)都是由類似方法產(chǎn)生,即

26、前兩項(xiàng)之和;所以求當(dāng)前項(xiàng)時(shí),只需要記住前兩項(xiàng);程序不需要為每一項(xiàng)設(shè)置專用變量; 屬遞推算法。,算法: 1、設(shè)置變量n表示第幾項(xiàng),變量 f 1和 f 2用來記住當(dāng)前項(xiàng)f 3之前的兩項(xiàng) ;變量初始化n=0; 2、while (當(dāng)前項(xiàng)不到第20項(xiàng)) if (當(dāng)前項(xiàng)是第0項(xiàng)) f 1=0; if (當(dāng)前項(xiàng)是第1項(xiàng)) f 2=1; if (當(dāng)前項(xiàng)是第2項(xiàng)或更高項(xiàng))f 3=f 1+f 2; 按要求輸出 f 3 ; f 1=f 2; f 2=f 3; /記住最近兩項(xiàng) 當(dāng)前項(xiàng)后移一位; ,【例311】 設(shè)計(jì)程序輸出Fibonacii數(shù)列的前20項(xiàng),要求每行輸出2個(gè)數(shù)據(jù)。Fibonacii數(shù)列定義如下: 程序如

27、下: /文件名:Ex3_11.cpp #include #include void main() int fib0=0,fib1=1,fib2; coutsetw(5)fib0setw(5)fib1 endl; for(int n=3;n=20;n+) fib2=fib0+fib1; coutsetw(5)fib2; if(n%5=0) coutendl; /控制每行2個(gè)數(shù)據(jù) fib0=fib1; fib1=fib2; ,for 語句的應(yīng)用,在VC+平臺(tái)上運(yùn)行 運(yùn)行結(jié)果: 0 1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597 2584 41

28、81,【例3.12】 輸入一個(gè)不超過5位的整數(shù),將其反向后輸出。例如輸入247,變成742輸出。 算法分析: 1、將整數(shù)的各個(gè)數(shù)位逐個(gè)位分開,用一個(gè)數(shù)組保存各個(gè)位的值,然后反向組成新的整數(shù)。 2、將整數(shù)各位數(shù)字分開的方法是,通過求余得到個(gè)位數(shù),然后將整數(shù)縮小十倍,再求余,并重復(fù)上述過程,分別得到十位、百位,直到整數(shù)的值變成0為止。,for 語句的應(yīng)用,ok,數(shù)據(jù): 1、設(shè)置變量num表示輸入的整數(shù),整型數(shù)組digit5用來存放num 的各個(gè)位;變量i用來表示數(shù)組的當(dāng)前下標(biāo); 算法: 1、輸入num; 變量初始化:i=0; 2、while (num!=0) num對(duì)10取余,得num的當(dāng)前個(gè)位數(shù)

29、digiti; num整除10,即去掉個(gè)位數(shù),十位變個(gè)位,百位變十位,; i+;數(shù)組digit準(zhǔn)備記錄下一位; 3、將數(shù)組元素按下標(biāo)從高到低的順序輸出;,程序如下: #include void main() int num,subscript; int digit5; coutnum; cout0); for(int i=0;isubscript;i+)/整數(shù)的反向組合 num=num*10+digiti; cout反向后整數(shù)為:numendl; 在VC+平臺(tái)上運(yùn)行,試一試是否正確,3.2.4 循環(huán)的嵌套,【例313】 打印九九表。打印格式為: * 1 2 3 4 5 6 7 8 9 1 1

30、2 2 4 3 3 6 9 9 9 18 27 36 45 54 63 72 81,當(dāng)循環(huán)語句中的循環(huán)體中又有循環(huán)語句時(shí),就構(gòu)成了嵌套循環(huán)。 嵌套層次一般不超過3層,已保證可讀性。,循環(huán)的嵌套,分析: 1、計(jì)算機(jī)的輸出是按行進(jìn)行的,因此可以先用一個(gè)循環(huán)語句輸出第一行表頭。 2、表中各行數(shù)據(jù)的輸出可以用下面的算法描述: for (i=1; i10; i+) couti; /輸出行號(hào) 輸出第i行數(shù)據(jù); /A coutendl; /準(zhǔn)備輸出下一行 ,3、第A行需要進(jìn)一步細(xì)化。由于第i行數(shù)據(jù)是一組有規(guī)律的數(shù)列,每個(gè)數(shù)的值是其所在行與列的乘積,因此輸出第i行可以: for (j=1; j10; j+)

31、coutsetw(4)i*j; 4、按上述算法輸出的每一行都將有九列,即打印出的是矩形表而不是下三角形表。進(jìn)一步分析發(fā)現(xiàn)每一行的列數(shù)與所在行數(shù)相關(guān),因此要輸出三角形表,上面的循環(huán)語句需稍作修改: for (j=1; j=i; j+) coutsetw(4)i*j; 將此語句放到頂層算法的A行即可。,循環(huán)的嵌套,算法: 1、輸出表頭,用一個(gè)循環(huán)語句即可; 2、輸出表體: for (i=1; i10; i+) couti; /輸出行號(hào) 輸出第i行數(shù)據(jù); /A coutendl; /準(zhǔn)備輸出下一行 3、A行細(xì)化: for (j=1; j=i; j+) coutsetw(4)i*j;,循環(huán)的嵌套,在V

32、C+平臺(tái)上運(yùn)行下面的程序: #include #include void main() coutsetw(3)*setw(4) ; for(int i=1;i10;i+) coutsetw(4)i; /輸出表頭(乘數(shù)) coutendlendl; for(i=1;i10;i+) coutsetw(3)isetw(4) ; /輸出行號(hào)(被乘數(shù)) for(int j=1;j=i;j+) coutsetw(4)i*j;/輸出表中數(shù)據(jù)(乘積) coutendl; /準(zhǔn)備輸出下一行 ,3.2.4 循環(huán)嵌套_打印九九表,3.3 轉(zhuǎn)向語句,331 break語句,334 return語句,333 goto

33、語句,332 continue語句,3.3.1 break 語句,break語句只能用在switch語句和循環(huán)語句中,用來跳出switch語句或提前終止循環(huán),轉(zhuǎn)去執(zhí)行switch語句或循環(huán)語句之后的語句。 在for循環(huán)中可以用break結(jié)束循環(huán): for(; ;) if() break; ,break 語句應(yīng)用,【例3.14】 給定正整數(shù)m,判定其是否為素?cái)?shù)。 分析:如果m2,m是素?cái)?shù)的條件是不能被2,3,,(取整)整除。因此可以用2,3,,(取整)逐個(gè)去除m,如果被其中某個(gè)數(shù)整除了,則m不是素?cái)?shù),否則是素?cái)?shù)。算法屬于窮舉法。 1、輸入被測(cè)數(shù)m(m2);令整型變量 k= sqrt(m) 2、判

34、斷m是否素?cái)?shù):設(shè)置輔助整型變量i, 使i從2開始直到k依次測(cè)試m能否整除i, 若能,則不是素?cái)?shù);for( i=2;i=k;i+)if(m%i=0) break; /* 條件滿足,m不是素?cái)?shù),停止測(cè)試,結(jié)束for語句。*/ 3、根據(jù)i是否已達(dá)到k,輸出結(jié)果是否為素?cái)?shù)。,#include #include void main() int m,i,k; coutm; if(m=2) coutk) cout m是素?cái)?shù)endl;/循環(huán)提前終止表示是非素?cái)?shù) else cout m不是素?cái)?shù)endl; 在VC+平臺(tái)上運(yùn)行,改一下,使程序自動(dòng)算出100以內(nèi)的素?cái)?shù),3.3.2 continue 語句,contin

35、ue語句只能用在循環(huán)語句中,用來終止本次循環(huán)。當(dāng)程序執(zhí)行到continue語句時(shí),將跳過其后尚未執(zhí)行的循環(huán)體語句,開始下一次循環(huán)。下一次循環(huán)是否執(zhí)行仍然取決于循環(huán)條件的判斷。 continue語句與break語句的區(qū)別在于,continue語句結(jié)束的只是本次循環(huán),而break結(jié)束的是整個(gè)循環(huán)。,例:輸出1100內(nèi)3的倍數(shù)。 分析:設(shè)置整型變量I從1變化到100,依次測(cè)試I是否3的倍數(shù),算法屬于窮舉法。 for (I=1;I=100;I+) if ( I%3!=0) continue; /I不是3的倍數(shù),不輸出,繼續(xù)下一個(gè)I; 輸出I的值;/I是3的倍數(shù)才輸出 ,3.3.3 goto 語句,go

36、to語句和標(biāo)號(hào)語句一起使用,所謂標(biāo)號(hào)語句是用標(biāo)識(shí)符標(biāo)識(shí)的語句,它控制程序從goto語句所在的地方轉(zhuǎn)移到標(biāo)號(hào)語句處。goto語句會(huì)導(dǎo)致程序結(jié)構(gòu)混亂,可讀性降低,而且它所完成的功能完全可以用算法的三種基本結(jié)構(gòu)實(shí)現(xiàn),因此一般不提倡使用goto語句。但在某些特定場(chǎng)合下goto語句可能會(huì)顯出價(jià)值,比如在多層循環(huán)嵌套中,要從深層地方跳出所有循環(huán),如果用break語句,不僅要使用多次,而且可讀性較差,這時(shí)goto語句可以發(fā)揮作用。,3.3.4 return 語句,return語句用于結(jié)束函數(shù)的執(zhí)行,返回調(diào)用者,如果是主函數(shù),則返回至操作系統(tǒng)。 利用一個(gè)return語句可以將一個(gè)數(shù)據(jù)返回給調(diào)用者。通常,當(dāng)函數(shù)

37、的返回類型為void時(shí), return語句可以省略,如果使用也僅作為函數(shù)或程序結(jié)束的標(biāo)志。,3.4 常用算法的應(yīng)用實(shí)例,【例3.15】 用歐基里德算法(也稱輾轉(zhuǎn)法)求兩個(gè)整數(shù)的最大公約數(shù)。 分析:假定兩個(gè)整數(shù)分別為num1和num2,最大公約數(shù)應(yīng)當(dāng)是不超過其中較小數(shù)的一個(gè)整數(shù)。 輾轉(zhuǎn)法的思想是:用num1除以num2,求出余數(shù)resd,如果resd=0,則當(dāng)前num2就是最大公約數(shù),否則如果resd!=0,num1=num2, num2=resd, 重復(fù)以上過程,直到resd=0為止。,【例3.15】,【例3.16】,【例3.17】,【例3.18】,1、設(shè)置兩個(gè)整型變量num1和num2代表兩

38、個(gè)數(shù);輸入num1、num2; 2、輾轉(zhuǎn)法: 2.1、使num1num2; 2.2.1、設(shè)置變量resd=num1%num2; 2.2.2、if(resd=0)當(dāng)前num2就是最大公 約數(shù); Else num1=num2, num2=resd; 重復(fù)2.2.1和2.2.2,直到resd=0為止。 2.2、do resd=num1%num2; if(resd=0)當(dāng)前num2就是最大公約數(shù); else num1=num2, num2=resd; while (resd!=0); 3、輸出當(dāng)前的num2。,程序如下: #include void main( ) int num1,num2; cou

39、tnum1num2; coutnum1和num2的最大公約數(shù)為:; for(;) int resd; resd=num1%num2; if(resd=0) break; num1=num2; num2=resd; coutnum2endl; ,【例316】 用篩選法求100之內(nèi)的所有素?cái)?shù),并將這些素?cái)?shù)輸出,每行輸出 2個(gè)數(shù)據(jù)。 分析 算法一 窮舉法: 1、判斷一個(gè)數(shù)是否素?cái)?shù)?方法窮舉法; 2、100之內(nèi)的所有素?cái)?shù)?方法:一個(gè)個(gè)試; 綜上所述,得到一個(gè)循環(huán)嵌套的算法: for(int m=2;m=100;k+)/窮舉法 if(m是素?cái)?shù))按要求的格式輸出k;,k= sqrt(m); for(i=2

40、;i=k;i+) /窮舉法 if(k%i=0) break; /k不是素?cái)?shù) if (i=k) k不是素?cái)?shù); /剛才的for是由break結(jié)束的,分析 算法二 篩選法: 1、一個(gè)數(shù)如果是其他數(shù)的倍數(shù),則這個(gè)數(shù)肯定不是素?cái)?shù); 2、在由 多個(gè)大于1的數(shù) 組成的集合中,剔除所有的非素?cái)?shù),剩下的就都是素?cái)?shù)了; 綜上所述,得到算法二(及所需的相應(yīng)數(shù)據(jù)): 1、將100之內(nèi)的整數(shù)映射到一個(gè)集合??梢圆捎靡粋€(gè)數(shù)組a來表示,數(shù)組元素值為各個(gè)整數(shù); 2、在數(shù)組a中,從素?cái)?shù)2開始剔除掉新找到的素?cái)?shù)的整數(shù)倍的元素值(置0,非素?cái)?shù)); 3、輸出數(shù)組a中數(shù)組元素值非0的元素,他們都是素?cái)?shù)。,算法二 第 2步 的細(xì)化(篩選

41、法): for (i=0; i=9; i+) /數(shù)組下標(biāo)09,元素值110 2.1、 if (ai=0) continue; / i已被定為非素?cái)?shù),已被篩掉 2.2、將數(shù)組中所有是ai倍數(shù)的元素置0; for(int j=i+1;j=99;j+) if(aj%ai=0) aj=0; 2.3、判定ai是否素?cái)?shù); if(ai不是素?cái)?shù)) ai=0; /ai肯定是素?cái)?shù) ,3.4 常用算法的應(yīng)用實(shí)例,#include #include #include const int n=100; void main() int an; int i,j; for(i=0;in;i+) ai=1+i; /用數(shù)組保存整

42、數(shù)1-100 a0=0; /1不是素?cái)?shù),置0 for(i=0;in;i+) if(ai=0) continue; /該數(shù)已經(jīng)置0,判斷下一個(gè) for(j=i+1;jn;j+)if(aj%ai=0) aj=0; /是ai倍數(shù)的元素置0; ,3.4 常用算法的應(yīng)用實(shí)例,int count=0; cout1 n之間的素?cái)?shù):endl; for(i=0;in;i+) /輸出所有素?cái)?shù) if(ai!=0) coutsetw(6)ai; count+; if(count%10=0) coutendl;/每行10個(gè) coutendl; 運(yùn)行結(jié)果:1100之間的素?cái)?shù): 2 3 5 7 11 13 17 19 23

43、 29 31 37 41 43 47 53 59 61 67 71 73 79 83 89 97,3.4 常用算法的應(yīng)用實(shí)例,3.4 常用算法的應(yīng)用實(shí)例,【例317】 世界數(shù)學(xué)史上著名的“百雞問題”:雞翁一,值錢五,雞母一,值錢三,雞雛三,值錢一。百錢買百雞,問雞翁、母、雛各幾何? 分析:設(shè)雞翁、母、雛分別為i,j,k,根據(jù)題意可得: i*5+j*3+k/3*1=100; i+j+k=100; 兩個(gè)方程無法解出三個(gè)變量,只能將各種可能的取值代入,其中能滿足兩個(gè)方程的就是所需的解,因此這是枚舉算法(也叫窮舉法)的應(yīng)用。 i、j、k可能的取值有哪些?分析可知,百錢最多可買雞翁20,雞母33,雞雛3

44、00。,算法: for (i=0; i=20;i+) for (j=0; j=33;j+) for (k=0; k=300;k+) if (i+j+k=100) 這個(gè)算法使用三重循環(huán),執(zhí)行時(shí)間函數(shù)是立方階,循環(huán)體將執(zhí)行20*33*300=198000次。 我們希望在算法上改進(jìn)一下,如能減少一重循環(huán),將大大縮短運(yùn)行時(shí)間。,3.4 常用算法的應(yīng)用實(shí)例,實(shí)際上,當(dāng)i、j確定時(shí),k就可由題目要求確定為100-i-j,因此實(shí)際上只要用i、j去測(cè)試,用錢數(shù)檢測(cè)就可以了。循環(huán)體將執(zhí)行: 20*33=660次。 算法改進(jìn)為: for (i=0; i+=20;) for (j=0; j+=33;) if ( 5

45、*i+3*j+(100-i-j)/3=100 ) coutijk;,3.4 常用算法的應(yīng)用實(shí)例,程序如下: #include #include void main() int i,j,k; cout 公雞 母雞 小雞endl; for(i=0;i=20;i+) for(j=0;j=33;j+) k=100-i-j; if(5*i+3*j+k/3=100) ,3.4 常用算法的應(yīng)用實(shí)例,程序運(yùn)行后將輸出: 公雞母雞小雞 0 25 75 4 18 78 8 11 81 12 4 84,3.4 常用算法的應(yīng)用實(shí)例,3.4 常用算法的應(yīng)用實(shí)例,【例3.18】 輸入一個(gè)8位二進(jìn)制數(shù),將其轉(zhuǎn)換為十進(jìn)制數(shù)輸

46、出。 分析:二進(jìn)制轉(zhuǎn)換為十進(jìn)制只要將每位二進(jìn)制數(shù)乘以該位的權(quán)然后相加。實(shí)際上屬于多項(xiàng)式求和問題: 對(duì)于本例,x=2。多項(xiàng)式的系數(shù)a i 即為二進(jìn)制數(shù)的各個(gè)位,可以用數(shù)組保存。 如果直接求冪再求和,需要做(n*(n+1)/2)次乘法?,F(xiàn)將多項(xiàng)式作如下變形: 就變成一個(gè)十分簡單的計(jì)算,僅做了n次乘法。,算法: 1、數(shù)組bin8用來放各個(gè)二進(jìn)制位; 2、整型變量dec= 0 ; x=2; /初始化 2、for(i=7;i=0;i-) /系數(shù)從a n 到a 0 依次投入運(yùn)算 dec = dec * x +(bini - 0 ); / (bini - 0 ):數(shù)字字符轉(zhuǎn)換為數(shù)字,3.4 常用算法的應(yīng)用實(shí)

47、例,程序如下: #include const int n=8; void main() char binn; int x=2,a,dec,i; cout=0;i-) cinbini;/先輸入的是高位 dec=0; for(i=n-1;i=0;i-) a=bini-0;/數(shù)字字符轉(zhuǎn)換為數(shù)字 dec= dec*x+a; cout=0;i-) coutbini; cout)的值為:decendl; ,3.5 枚舉類型,351 枚舉類型的定義,352 枚舉變量的使用,枚舉類型(enumerate)是c+中的一種派生數(shù)據(jù)類型,它是用戶定義的若干枚舉常量的集合。 枚舉類型的變量,只能取枚舉常量表中所列的值

48、。 定義枚舉類型的主要目的是增加程序的可讀性。,3.5.1 枚舉類型的定義,枚舉類型的定義格式為: enum ; 關(guān)鍵字enum指明其后的標(biāo)識(shí)符是一個(gè)類型的名字,枚舉常量表中列出該類型的所有取值,各枚舉常量之間以“,”間隔。例: enmu color_set1 RED, BLUE, WHITE, BLACK; enum week Sun, Mon, Tue, Wed, Thu, Fri, Sat; 枚舉常量(或稱枚舉成員)是以標(biāo)識(shí)符形式表示的整型量,例如下面的定義是非法的: enum letter_set a, d, F, s, T; /枚舉常量只能是標(biāo)識(shí)符 enum year_set2000

49、,2001,2002,2003,2004,2005; /改為y2000等則正確,3.5.1 枚舉類型的定義,各個(gè)枚舉常量代表該枚舉類型的變量可能取的值,編譯系統(tǒng)為每個(gè)枚舉常量指定一個(gè)整數(shù)值,缺省狀態(tài)下,這個(gè)整數(shù)就是所列舉元素的序號(hào),序號(hào)從0開始。如上例中RED、 BLUE、 WHITE、 BLACK的值分別為0、1、2、3。用戶也可以在類型定義時(shí)為部分或全部枚舉常量指定整數(shù)值,在第一個(gè)指定值之前的枚舉常量仍按缺省方式取值,而指定值之后的枚舉常量按依次加1的原則取值。各枚舉常量的值可以重復(fù),但各枚舉常量標(biāo)識(shí)符必須不同。例如, enum fruit_set apple, orange, banan

50、a=1, peach, grape enum week Sun=7, Mon=1, Tue, Wed, Thu, Fri, Sat; 枚舉常量apple、orange、banana、peach、grape的值分別為0、1、1、2、3。枚舉常量Sun, Mon, Tue, Wed, Thu, Fri, Sat的值分別為7、1、2、3、4、5、6。,3.5.2 枚舉類型的變量的使用,1、定義枚舉類型之后,就可以定義枚舉類型的變量;亦可類型與變量同時(shí)定義(甚至類型名可?。?color_set1 color1, color2; enum Sun, Mon, Tue, Wed, Thu, Fri, S

51、at weekday1, weekday2; 2、枚舉變量的取值范圍就是整型數(shù)的一個(gè)子集。枚舉變量占用內(nèi)存的大小與整型數(shù)相同。,3、枚舉變量允許的操作只有賦值和關(guān)系運(yùn)算;例如: if (color3=color4) coutcolor1/非法 coutcolor3/合法,輸出的是2 從程序的合法性和可讀性出發(fā),枚舉變量的輸入輸出一般都采用switch語句將其轉(zhuǎn)換為字符或字符串。同時(shí),枚舉類型數(shù)據(jù)的其他處理也往往應(yīng)用switch語句。,3.5.2 枚舉類型的變量的使用,【例319】 口袋中有紅、黃、藍(lán)、白、黑五種顏色的球若干個(gè),每次從口袋中取三個(gè)不同顏色的球,統(tǒng)計(jì)并輸出所有的取法。 分析: 每個(gè)球的顏色都是這五種顏色之一,因此可以使用枚舉類型來定義球的顏色。 假設(shè)所取三個(gè)球的顏色分別為i, j, k, 每個(gè)量都有5種取值,其中ijk就是滿足要求的取法,因此用枚舉算法(窮舉法)可以解決。,3.5.2 枚舉類型的變量的使用,算法: 1、定義枚舉類型及相應(yīng)變量; enum color red,yellow,blue,white,black; color i,j,k,col; 2、

溫馨提示

  • 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)論