c語言程序設(shè)計10第十講(第五章上)課件_第1頁
c語言程序設(shè)計10第十講(第五章上)課件_第2頁
c語言程序設(shè)計10第十講(第五章上)課件_第3頁
c語言程序設(shè)計10第十講(第五章上)課件_第4頁
c語言程序設(shè)計10第十講(第五章上)課件_第5頁
已閱讀5頁,還剩161頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

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

文檔簡介

不為失敗找理由、要為成功找方法!1不為失敗找理由、要為成功找方法!1高級語言程序設(shè)計主講教師:賈彩燕計算機(jī)與信息技術(shù)學(xué)院計算機(jī)科學(xué)與技術(shù)系cyjia@2高級語言程序設(shè)計主講教師:賈彩燕2第五章

C程序結(jié)構(gòu)3第五章

C程序結(jié)構(gòu)3本章討論與C程序整體結(jié)構(gòu)有關(guān)的問題。對正確理解C語言/正確書寫C程序很重要。學(xué)習(xí)用C程序設(shè)計時應(yīng)了解的“深層問題”。1)基本數(shù)值類型的全面介紹2)函數(shù)與C程序結(jié)構(gòu),函數(shù)原型3)變量類,作用域與存在期4)預(yù)處理命令5)字位運(yùn)算符(特殊問題,初步了解,需要時深入)4本章討論與C程序整體結(jié)構(gòu)有關(guān)的問題。1)基本數(shù)值類型的全面介主要內(nèi)容數(shù)值類型函數(shù)和標(biāo)準(zhǔn)庫函數(shù)函數(shù)定義和程序的函數(shù)分解C程序結(jié)構(gòu)與變量預(yù)處理命令定義常量字位運(yùn)算符編程實(shí)例5主要內(nèi)容數(shù)值類型55.1數(shù)值類型實(shí)數(shù)類型:float,double,longdouble實(shí)數(shù)類型外的算術(shù)類型都是整數(shù)類型。字符類型也看作整數(shù)類型,可以作為整數(shù)參加運(yùn)算。每一基本整數(shù)類型都有帶符號與無符號兩種類型,用限定詞signed或unsigned說明。無符號類型的值大于等于0。同一基本類型的帶符號/無符號類型用同樣長度編碼。signed可省略,如signedlong簡寫為long。65.1數(shù)值類型實(shí)數(shù)類型:float,double,lon字符類型:char,signedchar,unsignedchar用一個字節(jié)表示,其中存字符編碼。ASCII字符集里數(shù)字(字母)字符的編碼連續(xù)排列。char等同于signedchar或unsignedchar(不同系統(tǒng)可能不同)。簡單程序只用char,不需要關(guān)心有無符號。只有用char參加整數(shù)運(yùn)算時才需要考慮。基本ASCII字符集的編碼范圍是0-127。7字符類型:char,signedchar,unsigned整數(shù)類型

基本:int,shortint,longint總共六個: int unsignedint short unsignedshort long unsignedlongshortint簡寫為short,longint簡寫long,unsignedint簡寫為unsignedshort表示范圍不大于int,long不小于int。無符號/有符號類型位數(shù)相同。具體表示由C語言系統(tǒng)確定?;绢愋褪莍nt,一般用計算機(jī)的字長表示。16位機(jī)器的C系統(tǒng)中,int通常用16位表示;32位機(jī)器的C系統(tǒng)中,int通常用32位表示;8整數(shù)類型基本:int,shortint,longin整數(shù)常量可用十進(jìn)制八進(jìn)制(0開頭)十六進(jìn)制(0x或0X開頭)長整型加后綴L或lshort無常量寫法無符號數(shù)加后綴u或U123U,2987654LU,327LU,32014U無符號整數(shù)的算術(shù)運(yùn)算按取模方式做(不會溢出),超出表示范圍時取模作為計算結(jié)果。例:若16位unsignd范圍為0~65535。計算超范圍時取模65536。234U+65500U的計算結(jié)果是198U。9整數(shù)常量可用十進(jìn)制無符號整數(shù)的算術(shù)運(yùn)算按取模方式做(混合類型運(yùn)算前把小類型轉(zhuǎn)換到大類型的值。整數(shù)提升:小整數(shù)(short、char等)先轉(zhuǎn)為int值再運(yùn)算。若轉(zhuǎn)換結(jié)果超出int范圍(unsignedshort提升可能出問題),就提升為unsigned?;绢愋拖嗤瑫r,認(rèn)為無符號類型是比同樣的有符號類型更大的類型。例如做下面計算:2365U+18764將先由18764(整型值)轉(zhuǎn)換生成unsigned對應(yīng)值,再用此新值參與運(yùn)算。10混合類型運(yùn)算前把小類型轉(zhuǎn)換到大類型的值。基本類型相同時,認(rèn)為基本數(shù)據(jù)類型的選擇C語言提供多個浮點(diǎn)類型和整數(shù)類型,供編程者選擇使用。如無特殊需要,浮點(diǎn)數(shù)總用double,因其精度和范圍能滿足一般要求(float精度過低,longdouble可能低效,一般不用)。如無特殊需要,整數(shù)總用是C語言里最基本的類型,能得到硬件基本支持,其效率不會低于任何其他整數(shù)類型。有時用long類型。如無特殊需要,字符總采用char。盡量少用unsigned類型,除非服務(wù)于特殊目的。11基本數(shù)據(jù)類型的選擇C語言提供多個浮點(diǎn)類型和整數(shù)類型,供編程主要內(nèi)容數(shù)值類型函數(shù)和標(biāo)準(zhǔn)庫函數(shù)函數(shù)定義和程序的函數(shù)分解C程序結(jié)構(gòu)與變量預(yù)處理命令定義常量字位運(yùn)算符編程實(shí)例12主要內(nèi)容數(shù)值類型12編寫大程序時應(yīng)特別注意函數(shù)分解。沒有合理函數(shù)分解不可能完成復(fù)雜工作/多花時間/程序更難理解/錯誤更難發(fā)現(xiàn)和糾正。開始就應(yīng)強(qiáng)調(diào)好的編程習(xí)慣(包括函數(shù)分解)。函數(shù)的作用:把一段計算抽象出來,封裝(包裝)成獨(dú)立實(shí)體。這種封裝程序段稱為函數(shù)定義。定義后通過函數(shù)名就可以用簡便方式要求執(zhí)行該函數(shù)所封裝的計算。這種描述片段稱為函數(shù)調(diào)用。5.2函數(shù)和標(biāo)準(zhǔn)函數(shù)庫問題復(fù)雜使程序變長。大程序難開發(fā)/難閱讀理解/難修改;修改時容易破壞完整性,難保證不引進(jìn)新錯誤。程序中常出現(xiàn)許多相同/類似片段。使程序更長,增加不同部分間的聯(lián)系,損害可修改性。13編寫大程序時應(yīng)特別注意函數(shù)分解。函數(shù)的作用:把一段計算抽象出基本C語言很小,ANSIC定義了標(biāo)準(zhǔn)庫,其中提供最常用的與平臺無關(guān)的功能。每個符合標(biāo)準(zhǔn)的C系統(tǒng)都提供了標(biāo)準(zhǔn)庫,通常還提供一些擴(kuò)充庫,以便使用特定硬件/特定系統(tǒng)的功能:DOS上的C系統(tǒng)提供與DOS有關(guān)的功能函數(shù)Windows上的系統(tǒng)提供與Windows有關(guān)的函數(shù)UNIX系統(tǒng)上的系統(tǒng)提供與UNIX接口的函數(shù)擴(kuò)充庫不標(biāo)準(zhǔn),使用擴(kuò)充庫的程序依賴于具體系統(tǒng)。庫函數(shù)實(shí)現(xiàn)常用計算,可按規(guī)定方式調(diào)用,不必自己實(shí)現(xiàn)/不必關(guān)心怎樣實(shí)現(xiàn)。開發(fā)一次使所有用戶受益。C語言的庫函數(shù)14基本C語言很小,ANSIC定義了標(biāo)準(zhǔn)庫,其中提供最常用的與標(biāo)準(zhǔn)庫功能包括

輸入輸出、文件操作、存儲管理,其他如數(shù)學(xué)函數(shù)、數(shù)據(jù)轉(zhuǎn)換函數(shù)等。有關(guān)介紹散布在各章,后面有詳細(xì)介紹。對具體C系統(tǒng)的擴(kuò)充庫可查閱系統(tǒng)聯(lián)機(jī)幫助,或查閱有關(guān)手冊、參考書籍。。下面介紹兩組常用標(biāo)準(zhǔn)函數(shù)。15標(biāo)準(zhǔn)庫功能包括下面介紹兩組常用標(biāo)準(zhǔn)函數(shù)。15字符分類(<ctype.h>)isalpha(c) c是字母字符isdigit(c)c是數(shù)字字符isalnum(c) c是字母或數(shù)字字符isspace(c) c是空格、制表符、換行符isupper(c) c是大寫字母islower(c) c是小寫字母iscntrl(c) c是控制字符isprint(c)c是可打印字符,包括空格isgraph(c) c是可打印字符,不包括空格isxdigit(c) c是十六進(jìn)制數(shù)字字符ispunct(c) c是標(biāo)點(diǎn)符號inttolower(intc) 轉(zhuǎn)為對應(yīng)小寫字母inttoupper(intc) 轉(zhuǎn)為對應(yīng)大寫字母是返回非零,不是返回零16字符分類(<ctype.h>)isalpha(c) #include<stdio.h>#include<ctype.h>intmain(){intc,cd=0,cu=0,cl=0;while((c=getchar())!=EOF){if(isdigit(c))++cd;if(isupper(c))++cu;if(islower(c))++cl;}

printf("digits:%d\n",cd);

printf("uppers:%d\n",cu);

printf("lowers:%d\n",cl);return0;}用標(biāo)準(zhǔn)庫函數(shù)完成判斷比自己寫條件更合適。

17#include<stdio.h>用標(biāo)準(zhǔn)庫函數(shù)完成判斷比自#include<stdio.h>#include<ctype.h>intmain(){intcount=0,c;while((c=getchar())!=EOF){if(isspace(c))continue;++count;while((c=getchar())!=EOF&&!isspace(c));}

printf("Words:%d\n",count);return0;}統(tǒng)計單詞程序:18#include<stdio.h>統(tǒng)計單詞程序:18隨機(jī)數(shù)生成函數(shù)程序調(diào)試:用數(shù)據(jù)做運(yùn)行試驗(yàn),隨機(jī)數(shù)據(jù)非常合適。計算機(jī)模擬:模擬實(shí)際情況/過程,客觀事物變化有隨機(jī)性。最常用的是除余定義:

a0=A an=(B×an-1+C)modDA,B,C,D為常數(shù),0≤A<D。適當(dāng)選擇B、C可產(chǎn)生0到D-1的較好隨機(jī)數(shù)列。計算機(jī)只能生成“偽隨機(jī)數(shù)”。常用方法是定義某種遞推關(guān)系,設(shè)法使序列中的數(shù)比較具有隨機(jī)性。19隨機(jī)數(shù)生成函數(shù)最常用的是除余定義:計算機(jī)只能生成“偽隨機(jī)數(shù)標(biāo)準(zhǔn)庫提供隨機(jī)數(shù)功能,需要包含文件<stdlib.h>。隨機(jī)數(shù)生成函數(shù):intrand(void)無參數(shù),得到0和符號常量

RAND_MAX

間的隨機(jī)整數(shù)。不同系統(tǒng)的RAND_MAX可能不同,至少為32767。函數(shù)srand用seed值設(shè)種子值:voidsrand(unsignedseed)默認(rèn)初始種子值是1;rand根據(jù)當(dāng)時種子值生成下一隨機(jī)數(shù)并修改種子值。20標(biāo)準(zhǔn)庫提供隨機(jī)數(shù)功能,需要包含文件<stdlib.h>。函數(shù)根據(jù)下面公式可以得到所需范圍內(nèi)的隨機(jī)數(shù):n=a+rand()%b其中a為位移,是所需連續(xù)整數(shù)范圍的第一個數(shù),b是比例因子,是所需連續(xù)整數(shù)范圍的寬度,則希望產(chǎn)生1--6之間隨機(jī)數(shù)的公式為:n=1+rand()%6希望產(chǎn)生0—1之間隨機(jī)數(shù)的公式為:n=rand()%2偽隨機(jī)數(shù)的產(chǎn)生

21根據(jù)下面公式可以得到所需范圍內(nèi)的隨機(jī)數(shù):偽隨機(jī)數(shù)的產(chǎn)生21例:編寫一個投擲骰子的程序,模擬10次,輸出每次投擲的點(diǎn)數(shù)。#include<stdio.h>#include<stdlib.h>intmain(){inti;printf(“\n”);

for(i=1;i<=10;i++)printf("%3d",1+rand()%6);return0;}結(jié)果:6655651153第二次運(yùn)行:6655651153使用srand函數(shù),通過提供不同的種子產(chǎn)生不同的隨機(jī)數(shù)序列。srand(x);

/*初始化隨機(jī)數(shù)發(fā)生器*/

unsignedx;

scanf(“%d”,&x);/*輸入一個非負(fù)的整數(shù)做種子*/16134356526233315356541516134356526222例:編寫一個投擲骰子的程序,模擬10次,輸出每次投擲的點(diǎn)數(shù)。#include<stdio.h>#include<stdlib.h>voidmain(){inti;printf(“\n”);

for(i=1;i<=10;i++)printf("%3d",1+rand()%6);}結(jié)果:3453314315再次運(yùn)行:4432355323

srand(time(NULL));/*使用time函數(shù)返回值做種子*/#include<time.h>例:編寫一個投擲骰子的程序,模擬10次,輸出每次投擲的點(diǎn)數(shù)23#include<stdio.h>結(jié)果:srand(主要內(nèi)容數(shù)值類型函數(shù)和標(biāo)準(zhǔn)庫函數(shù)函數(shù)定義和程序的函數(shù)分解C程序結(jié)構(gòu)與變量預(yù)處理命令定義常量字位運(yùn)算符編程實(shí)例24主要內(nèi)容數(shù)值類型245.3函數(shù)定義和程序的函數(shù)分解一個C程序主要是一系列的函數(shù)定義。函數(shù)定義形式:

函數(shù)頭部---

返回值類型函數(shù)名參數(shù)表

函數(shù)體庫函數(shù)有限,編寫復(fù)雜程序時需要自己定義函數(shù)。函數(shù)頭部:描述函數(shù)外部與函數(shù)內(nèi)部的聯(lián)系。

應(yīng)該總寫返回類型,無返回值用void說明。允許任意多個參數(shù),無參函數(shù)用(void)

(早期C語言對ANSIC的影響),定義無參函數(shù)時也可用()。255.3函數(shù)定義和程序的函數(shù)分解一個C程序主要是一系列的函數(shù)主函數(shù)mainmain的返回值規(guī)定為int。這個返回值在程序結(jié)束時送給外部,程序外部(如操作系統(tǒng))可用這個值。一般返回0表示程序正常結(jié)束,其他值表示出錯main以外的函數(shù)只有被調(diào)用時才會執(zhí)行不允許調(diào)用mainintmain(){/*一般寫法*/......return0;}26主函數(shù)mainintmain()262727程序的函數(shù)分解什么樣的程序片段應(yīng)該定義為函數(shù):重復(fù)出現(xiàn)的相同/相似計算片段,可設(shè)法抽取性定義為函數(shù)。長計算過程中有邏輯獨(dú)立性的片段,即使出現(xiàn)一次也可定義為函數(shù),以分解復(fù)雜性。經(jīng)驗(yàn)原則:可以定義為函數(shù)的內(nèi)容,就應(yīng)該定義為函數(shù);一個函數(shù)一般不超過一頁。往往存在很多可行的分解,尋找合理有效的分解是需要學(xué)習(xí)。28程序的函數(shù)分解什么樣的程序片段應(yīng)該定義為函數(shù):經(jīng)驗(yàn)原則:可以實(shí)例研究:字符圖形寫程序打印下面這類字符圖形最“簡單”的方式:用一系列putchar調(diào)用打印星號和空格(數(shù)清字符個數(shù),就可以寫出程序)。29實(shí)例研究:字符圖形寫程序打印下面這類字符圖形最“簡單”的方式方法二:程序里寫一系列printf調(diào)用。例:intmain(){/*打印菱形*/printf("*");printf("**");printf("***);....../*下略*/}不好!若要修改圖形大小或形式,程序需全部重寫如果需要畫出新圖形,已做工作對新工作毫無價值應(yīng)考慮畫這類圖形的“基本動作”,定義為函數(shù)。30方法二:程序里寫一系列printf調(diào)用。例:不好!若要修改圖分析:圖形由以下部分組成1)一段連續(xù)字符;2)在兩個特定位置的字符;字符圖形未必用星號,可推廣,引進(jìn)一個字符參數(shù)voidline(charc,intbegin,intend)voidpoints(charc,intfst,intsnd)

可考慮定義兩個函數(shù),其頭部分別為:

voidline(intbegin,intend)voidpoints(intfst,intsnd)line從begin到end輸出*,points在fst和snd輸出*。

31分析:字符圖形未必用星號,可推廣,引進(jìn)一個字符參數(shù)可考慮定義如函數(shù)已經(jīng)定義,畫菱形程序段可寫為:

for(i=10,j=10;i>4;--i,++j)points('*',i,j);

for(i+=2,j-=2;i<=j;++i,--j)points('*',i,j);

/*10是常量,確定菱形的位置和大小*/畫其他空心或?qū)嵭牡囊?guī)范圖形也不難。函數(shù)使用者只需考慮函數(shù)的使用形式和功能,無需考慮函數(shù)實(shí)現(xiàn)32如函數(shù)已經(jīng)定義,畫菱形程序段可寫為:函數(shù)使用者只需考慮函數(shù)的voidline(charc,intbegin,intend){inti;for(i=0;i<begin;++i)putchar('');for(;i<=end;++i)putchar(c);putchar('\n');}voidpoints(charc,intfirst,intsecond){inti;for(i=0;i<first;++i)putchar('');putchar(c);for(++i;i<second;++i)putchar('');if(first<second)putchar(c);putchar('\n');}做好了一個圖形后,修改其大小或形狀也比較容易。兩個函數(shù)是輸出一些空格和字符后換行:33voidline(charc,intbegin,i也可引入附加參數(shù),將兩個函數(shù)合而為一:voidline(charc,intbegin,intend,intfill){......}在fill為0值時在兩端點(diǎn)輸出,非0時連續(xù)輸出字符。還可基于它們定義畫各種基本幾何圖形的函數(shù)。設(shè)計函數(shù)時需要選定合適參數(shù)。例如畫矩形的函數(shù):voidrect(charc,intbegin,intlen,inthigh){......}這些函數(shù)又形成另一層抽象層次。定義好這樣一組函數(shù)后,就可以在新的層次上寫字符圖形程序了。34也可引入附加參數(shù),將兩個函數(shù)合而為一:還可基于它們定義畫各種封裝把函數(shù)內(nèi)外隔成兩個世界。不同世界形成了對函數(shù)的兩種觀點(diǎn)。函數(shù)頭規(guī)定了兩個世界的交流方式。對函數(shù)的兩種視點(diǎn)35封裝把函數(shù)內(nèi)外隔成兩個世界。不同世界形成了對函數(shù)的兩種觀點(diǎn)。函數(shù)是獨(dú)立的邏輯實(shí)體。定義后可以調(diào)用執(zhí)行。由此形成對函數(shù)的兩種觀察方式:1)從函數(shù)外(以函數(shù)使用者的角度)看函數(shù);2)在函數(shù)內(nèi)(以函數(shù)定義者的角度)看函數(shù)。計劃函數(shù)時,分析確定函數(shù)頭部,定好公共規(guī)范。寫函數(shù)定義時應(yīng)站在內(nèi)部觀點(diǎn)思考/解決問題;使用函數(shù)時應(yīng)站在外部立場上思考/解決問題。功能描述清楚,接口定義好以后,函數(shù)定義和使用可由不同人做。要求雙方遵循共同規(guī)范,對函數(shù)功能有一致理解。36函數(shù)是獨(dú)立的邏輯實(shí)體。定義后可以調(diào)用執(zhí)行。由此形成對函數(shù)的兩函數(shù)定義解決實(shí)現(xiàn)函數(shù)的算法問題和語言問題。參數(shù)是局部變量,調(diào)用時對應(yīng)實(shí)際參數(shù)賦初值,然后開始執(zhí)行函數(shù)體。參數(shù)像其他局部變量一樣可以賦值。return語句的執(zhí)行導(dǎo)致函數(shù)結(jié)束。return語句的兩種形式: return;/*無返回值*/return表達(dá)式;函數(shù)體里可有多個return語句。在帶不帶表達(dá)式/所帶表達(dá)式的類型方面必須與函數(shù)頭部一致。執(zhí)行到函數(shù)體末端時函數(shù)結(jié)束(無返回值的函數(shù))。37函數(shù)定義return語句的執(zhí)行導(dǎo)致函數(shù)結(jié)束。函數(shù)體里可有多個函數(shù)調(diào)用調(diào)用函數(shù)時必須提供數(shù)目正確/類型合適的實(shí)參。調(diào)用無參函數(shù)時也需要寫圓括號。無返回值函數(shù)用在獨(dú)立的函數(shù)調(diào)用語句里:pc_area(x+3);有返回值的函數(shù)通常用在表達(dá)式里。返回值也可不用。例:printf返回int。工作正常時返回實(shí)際輸出的字符數(shù),出錯時返回負(fù)值。38函數(shù)調(diào)用38C語言的參數(shù)機(jī)制稱為值參數(shù)(簡稱值參)f內(nèi)對a和b的操作與m和n沒有任何關(guān)系39C語言的參數(shù)機(jī)制稱為值參數(shù)(簡稱值參)f內(nèi)對a和b的操作與m值傳遞與賦值和初始化類似,可能出現(xiàn)轉(zhuǎn)換。要求實(shí)參值可轉(zhuǎn)換到形參類型,否則是類型錯。語言沒有規(guī)定調(diào)用時的實(shí)參求值順序,對求值順序敏感的函數(shù)調(diào)用是錯誤(與二元運(yùn)算類似)。例: n=...; m=gcd(n+=15,n);另一錯誤調(diào)用: printf("%d,%d",n++,n);C函數(shù)的參數(shù)是值參數(shù)函數(shù)調(diào)用時先計算實(shí)參表達(dá)式的值,把值復(fù)制給對應(yīng)形參,而后執(zhí)行函數(shù)體。函數(shù)內(nèi)對形參的操作與實(shí)參無關(guān)。40值傳遞與賦值和初始化類似,可能出現(xiàn)轉(zhuǎn)換。要求實(shí)參值可轉(zhuǎn)換到形命名對象(變量/函數(shù)等):基本規(guī)則是先定義后使用。保證正確編譯的基本原則:從每個對象的每個使用點(diǎn)向前看,能得到使用該對象的完備信息。局部變量:變量定義在語句前,保證了先定義后使用。后面變量定義可引用前面已經(jīng)定義的變量。函數(shù):使用點(diǎn)所需信息就是函數(shù)的類型特征,包括函數(shù)名/參數(shù)個數(shù)和類型/返回值類型等。調(diào)用位置要檢查參數(shù)個數(shù)和類型,是否需要以及能否轉(zhuǎn)換。返回值類型是否匹配。函數(shù)原型41命名對象(變量/函數(shù)等):基本規(guī)則是先定義后使用。調(diào)用位置要longfact(longn){returnn<=1?1:n*fact(n-1);}典型例子:inth(intx) intg(inty){.... { ......g(...).. ..h(...)...... ....} }這是引進(jìn)函數(shù)原型說明的一個原因。更重要的是使人能自由安排函數(shù)定義位置,支持大型程序開發(fā)。將主函數(shù)寫在最后就是為保證函數(shù)定義與使用的關(guān)系。遞歸定義的函數(shù)也能保證定義與使用的關(guān)系。有些情況無法通過安排函數(shù)定義位置解決。42longfact(longn)典型例子:這是引進(jìn)函數(shù)原原型說明的形式與函數(shù)頭部類似,加分號。參數(shù)名可省略,可與函數(shù)定義用的名字不同。任何可以寫定義的地方都可以寫原型說明。提倡把原型說明都放在程序文件最前面:1)使文件里所有調(diào)用能看到同一個原型說明。2)使函數(shù)的定義點(diǎn)也能看到同一個原型說明。原型說明是保證函數(shù)定義/使用間一致性的媒介。為保證原型能起作用,應(yīng)給出完整的類型特征voidline(charc,intbegin,intend);voidpoints(charc,intfst,intsnd);43原型說明的形式與函數(shù)頭部類似,加分號。任何可以寫定義的地方都過時的函數(shù)定義形式/原型形式C標(biāo)準(zhǔn)化時保留了一些過時東西,以保證老程序合法。這里介紹老形式只是為能讀別人寫的老程序。過時函數(shù)定義形式。例:doublef1(x,y,n)doublex,y;intn;{/*函數(shù)體*/}/*早期高級程序語言中常見的形式*/過時原型形式:設(shè)完整原型為doublef(double);intg(double,int);intmain(void){intg(),n;doublef(),x;....x=f(3);n=g(n);....}/*錯,編譯程序不會發(fā)現(xiàn)!*/不要使用過時函數(shù)定義和原型形式44過時的函數(shù)定義形式/原型形式不要使用過時函數(shù)定義和原型形式4不寫函數(shù)原型為寬容老程序,C語言容許不寫原型。遇到調(diào)用f(...),若此前無f定義或原型就做默認(rèn)處理,方式是假設(shè)有一個原型說明:intf();出現(xiàn)在包含該函數(shù)調(diào)用的最內(nèi)層復(fù)合語句的最前面,按此假設(shè)對函數(shù)調(diào)用進(jìn)行編譯和處理。只有f確實(shí)返回int,調(diào)用的實(shí)參個數(shù)和類型都與f的要求完全相同(不需轉(zhuǎn)換)時才能產(chǎn)生正確結(jié)果。不寫原型可能引起許多問題。是極危險的編程習(xí)慣!45不寫函數(shù)原型不寫原型可能引起許多問題。是極危險的編程習(xí)慣!4為避免函數(shù)使用的隱含錯誤,應(yīng)堅(jiān)持正確編程原則:如果使用標(biāo)準(zhǔn)庫,必須#include必要的庫文件所有使用前未給出定義的函數(shù)(無論實(shí)際上在哪里定義),都必須給出正確完整的原型說明應(yīng)把原型說明寫在源文件最前面基本原則:使函數(shù)的定義點(diǎn)和所有使用點(diǎn)都能“看到”同一個原型說明。堅(jiān)持這些原則,就能避免函數(shù)調(diào)用與定義不一致的錯誤(常常是編譯程序檢查不到的隱含致命錯誤)。簡單地說“用C語言編程序容易出錯”并不合理。許多錯誤是由于人們沒按正確地方式做事情。46為避免函數(shù)使用的隱含錯誤,應(yīng)堅(jiān)持正確編程原則:簡單地說“用C程序?qū)嵗?求函數(shù)的根)求函數(shù)根是典型數(shù)值計算問題,這里討論弦線法。解題思路:選定區(qū)間,兩端點(diǎn)函數(shù)值異號;做過端點(diǎn)弦線;求弦線與坐標(biāo)軸交點(diǎn);縮小區(qū)間,重復(fù)操作;直到交點(diǎn)函數(shù)值充分接近0(滿意為止)。47程序?qū)嵗?求函數(shù)的根)解題思路:47求弦線與坐標(biāo)軸交點(diǎn)的公式:1、輸入x1和x2,求f(x1)和f(x2),若f(x1)*f(x2)>0,轉(zhuǎn)1;否則轉(zhuǎn)22、根據(jù)x1和x2求x(定義函數(shù)crossp),求f(x)(定義函數(shù)f);3、檢查f(x)與f(x1)和f(x2)誰同號,重新選定x1或x2若f(x1)*f(x)>0則x1=x,否則,x2=x,4、檢查f(x)>=1E-6是否滿足,滿足轉(zhuǎn)2不滿足,結(jié)束,輸出x,為根。48求弦線與坐標(biāo)軸交點(diǎn)的公式:1、輸入x1和x2,求f(x1#include<stdio.h>#include<math.h>doublef(doublex){/*例子,根據(jù)需要定義*/returnx*((2*x-4)*x+3)-6;}doublecrossp(doublex1,doublex2){doubley1=f(x1),y2=f(x2);return(x1*y2-x2*y1)/(y2-y1);}49#include<stdio.h>49doubleroot(doublex1,doublex2){doublex,y,y1=f(x1);do{x=crossp(x1,x2);y=f(x);if(y*y1>0){/*y與y1同符號,新區(qū)間[x,x2]*/x1=x;y1=y;}elsex2=x;/*異號,新區(qū)間[x1,x]*/}while(fabs(y)>=1E-6);/*繼續(xù)*/returnx;}50doubleroot(doublex1,doubleintmain(){doublex1,x2,x;do{printf(“Inputdoublex1,x2”);scanf(“%lf%lf”,&x1,&x2);}while(f(x1)*f(x2)>0);

x=root(x1,x2);printf(“rootis%lf”,x);return0;}51intmain()51主要內(nèi)容數(shù)值類型函數(shù)和標(biāo)準(zhǔn)庫函數(shù)函數(shù)定義和程序的函數(shù)分解C程序結(jié)構(gòu)與變量預(yù)處理命令定義常量字位運(yùn)算符編程實(shí)例52主要內(nèi)容數(shù)值類型52變量定義:1)定義特定類型的變量;2)為變量命名。還確定了:變量定義的作用域:變量定義起作用的范圍。由定義位置確定,在此范圍可通過該名字使用該變量變量的存在期:確定變量建立和銷毀時間。各種變量的存在期可能不同。變量實(shí)現(xiàn)的基礎(chǔ)是內(nèi)存單元,存在期就是變量被分配內(nèi)存存儲到撤消的期間作用域與生存期變量的作用域決定了其生存期。5.4程序結(jié)構(gòu)與變量53變量定義:1)定義特定類型的變量;2)為變量命名。作用域與生作用域是靜態(tài)概念,一個變量的作用域是一段源程序。如在函數(shù)體開始定義的變量,作用域是整個函數(shù)體。生存期是動態(tài)概念,程序執(zhí)行的一段時間。變量在生存期中保持其存儲單元,不經(jīng)賦值那里的值就不變。在作用域和生存期方面,外部變量和局部變量性質(zhì)不同。外部變量:在所有的函數(shù)之外定義的變量稱為外部變量(或叫做全局變量).其作用范圍是從變量定義的位置開始,直到本源文件的結(jié)束。局部變量:在一個函數(shù)內(nèi)部定義或復(fù)合語句內(nèi)定義的變量,其作用范圍為函數(shù)體內(nèi)部或復(fù)合語句內(nèi)。從作用域的角度:54作用域是靜態(tài)概念,一個變量的作用域是一段源程序。如在函數(shù)體開1、一個源文件可以包含一個或幾個函數(shù).2、外部變量可以被本源文件的所有函數(shù)共享.3、外部變量的設(shè)置增強(qiáng)了函數(shù)間數(shù)據(jù)的聯(lián)系.一個函數(shù)對外部變量的值的改變將會影響到其他的函數(shù)中.4、建議在只有必要時才設(shè)置外部變量.5、外部變量在文件的開頭定義,則它的有效范圍是整個源文件,但如果全局變量不是在開頭定義的,則它有效范圍是從定義點(diǎn)到源文件的結(jié)束.6、外部變量可以后定義先使用,或在一個源文件里定義在其他文件使用。使用前應(yīng)給出外部變量說明(該變量一定在其它地方有定義)。形式:前面加關(guān)鍵詞extern。例:externintn,m;本程序可以使用該變量。外部變量的要點(diǎn):外部說明通常放在源文件最前面,供整個文件參照。更重要的:保證整個程序參照同一說明,保證一致性。551、一個源文件可以包含一個或幾個函數(shù).外部變量的要點(diǎn):外部說intp=1,q=1;/*定義外部變量p,q*/voidfloatf1(inta)/*定義函數(shù)f1*/{intb,c;…}charc1,c2;/*定義外部變量c1,c2*/voidcharf2(intx,inty)/*定義函數(shù)f2*/{inti,j;…}voidmain()

{intm,n;…}外部變量p,q的有效范圍外部變量c1,c2的有效范圍56intp=1,q=1;/*定義外部變量p,q*/外部外部5……intnum;externintexnumber;intf(intn){intn;….n…num…extnumber……….}intexnumber;intmain(){…f(…)…….num…extnumber……….}外部變量定義外部變量說明如果一個函數(shù)定義用到外部變量,它就依賴這些變量,不再獨(dú)立。注意:定義和說明不同。定義要求創(chuàng)建被定義的對象;說明只指明其存在,必須另有定義,否則該說明無效。外部變量可在整個程序用,在一個完整程序里不能有重名外部變量。否則連接時會出問題不要與函數(shù)庫里內(nèi)容重名(標(biāo)準(zhǔn)庫定義了一批外部名字)。57……外部變量定義外部變量說明如果一個函數(shù)定義用到外部變量,它1、主函數(shù)(main函數(shù))中定義的變量也只在主函數(shù)中有效;2、不同的函數(shù)中可使用相同的變量名,它們代表不同的含義;3、形參也是局部變量;4、在一個函數(shù)內(nèi)部可以使用復(fù)合語句來定義變量,這樣的變量只在本復(fù)合語句中有效.5、當(dāng)外部變量名與局部變量名相同時,則在局部變量的有效范圍內(nèi)外部變量不起作用.局部變量的要點(diǎn)581、主函數(shù)(main函數(shù))中定義的變量也只在主函數(shù)中有效;局inta=13,b=-8;intplus(intx,inty){intz;z=x+y;a=a+b;printf(“%d\n”,a)returnz;}intmian()

{intz;inta=6;z=plus(a,b);printf(“%d\n”,z);printf(“%d\n”,a)return0;}例分析下面的程序?qū)懗鼋Y(jié)果.5-2659inta=13,b=-8;例分析下面的程序?qū)懗鼋Y(jié)變量的存儲類別從變量存在時間(生存期)角度來區(qū)分:1、靜態(tài)存儲變量:在程序運(yùn)行期間分配固定的存儲空間的方式。2、動態(tài)存儲變量:在程序運(yùn)行期間根據(jù)需要進(jìn)行動態(tài)的分配存儲空間的方式。60變量的存儲類別從變量存在時間(生存期)角度來區(qū)分:60內(nèi)存中用戶區(qū)的劃分程序區(qū)靜態(tài)存儲區(qū)動態(tài)存儲區(qū)1.程序區(qū):存放程序的代碼;2.靜態(tài)存儲區(qū):存放全局變量和靜態(tài)的局部變量;3.動態(tài)存儲區(qū):存放局部變量,函數(shù)調(diào)用時的現(xiàn)場保護(hù)和返回地址;存放在靜態(tài)存儲區(qū)中的變量的生存周期是程序的整個執(zhí)行過程。存放在動態(tài)存儲區(qū)中的變量的生存周期是函數(shù)或復(fù)合語句的執(zhí)行期間。61內(nèi)存中用戶區(qū)的劃分程序區(qū)靜態(tài)存儲區(qū)動態(tài)存儲區(qū)1.程序區(qū):存放1、含義:指數(shù)據(jù)在內(nèi)存中的存儲方法。2、劃分:在c語言中將變量和函數(shù)的屬性劃分為:數(shù)據(jù)類型數(shù)據(jù)的存儲類別.如:staticinta,b;3、存儲類別:自動變量(auto)靜態(tài)變量(static)寄存器變量(register)外部變量(extern)分別放在靜態(tài)存儲區(qū)和動態(tài)存儲區(qū).變量和函數(shù)的存儲類別存貯類別數(shù)據(jù)類型621、含義:指數(shù)據(jù)在內(nèi)存中的存儲方法。變量和函數(shù)的存儲類別存貯1、含義:函數(shù)或復(fù)合語句中定義的變量不作特殊說明都為自動局部變量,存儲在動態(tài)存儲區(qū)。2、用法:用關(guān)鍵字auto進(jìn)行說明,可以省略auto關(guān)鍵字。intf(inta){autointb=0,c=10;..}3、要點(diǎn):當(dāng)函數(shù)調(diào)用結(jié)束或復(fù)合語句結(jié)束后,它們所占用的存儲空間即被釋放.自動變量631、含義:函數(shù)或復(fù)合語句中定義的變量不作特殊說明都為自動局部1、含義:函數(shù)中的局部變量的值在函數(shù)調(diào)用結(jié)束后不消失而保留原值。(即所占用的存儲單元并不釋放,下次直接使用)2、用法:用static說明。靜態(tài)局部變量intf(inta){autointb=0;staticintc=3;b+=1;c+=1;return(a+b+c);}intmain(){inta=2,i;for(i=0;i<3;i++)printf(“%3d”,f(a));return0;}運(yùn)行結(jié)果:7 89641、含義:函數(shù)中的局部變量的值在函數(shù)調(diào)用結(jié)束后不消失而靜態(tài)局1.靜態(tài)局部變量存儲在靜態(tài)存儲區(qū),在程序的整個運(yùn)行期間都不釋放;2.靜態(tài)局部變量是在編譯時賦初值的,即只賦值一次。3.靜態(tài)局部變量在定義時不賦初值,編譯時系統(tǒng)自動賦初值0;而對于自動變量,如果不賦初值則它的值是一個不確定的值.4.靜態(tài)局部變量在函數(shù)調(diào)用結(jié)束后仍然存在,但只能被這個函數(shù)再次使用,不能被其他函數(shù)使用.說明:651.靜態(tài)局部變量存儲在靜態(tài)存儲區(qū),在程序的整個運(yùn)行期間都不釋靜態(tài)局部變量實(shí)例假設(shè)需要一個函數(shù),調(diào)用時通常輸出空格,調(diào)用第10次時輸出換行符。取名format,無參??捎盟脑齑蛴⊥耆椒綌?shù)程序,使每行輸出10個數(shù):

for(n=1;n*n<=200;n++){printf("%d",n*n);

format();}許多地方都可能用它。初看這個函數(shù)可能很簡單。66靜態(tài)局部變量實(shí)例初看這個函數(shù)可能很簡單。66voidformat(void){

intm=0;if(++m==10){putchar('\n');m=0;}elseputchar('');}這個函數(shù)無論調(diào)用多少次都不輸出換行。m是自動變量,每次調(diào)用重新建立并初始化為0。無論調(diào)用format多少次,m也不可能等于10。67voidformat(void)這個函數(shù)無論調(diào)用多少次都可采用外部變量,存在期長,能保持值不變,可在任何函數(shù)(包括format)里使用。

intm=0;voidformat(void){if(++m==10){putchar('\n');m=0;}elseputchar('');}/*功能正確*/問題:程序其他部分可能不當(dāng)心修改了m(例如把局部變量n寫成m),導(dǎo)致計數(shù)錯誤。信息隱蔽/保護(hù)很重要,小到程序的組織,大到關(guān)系國家安全的重要系統(tǒng),都必須關(guān)注這個問題。68可采用外部變量,存在期長,能保持值不變,可在任何函數(shù)(包括f需要一種變量:局部作用域,限制在函數(shù)內(nèi),防止越權(quán)訪問;全程存在期和一次初始化,以便在函數(shù)調(diào)用之間傳遞信息,值在不同調(diào)用之間保持不變。靜態(tài)局部變量:定義時加static。voidformat(void){

staticintm=0;if(++m==10){putchar('\n');m=0;}elseputchar('');}需要局部作用域/全程存在期的變量,應(yīng)使用static。69需要一種變量:局部作用域,限制在函數(shù)內(nèi),防止越權(quán)訪問;全程存典型應(yīng)用:隨機(jī)數(shù)生成函數(shù)。生成隨機(jī)數(shù)需要前次遞推值(種子值),可選擇靜態(tài)局部變量intrandom(){

staticunsignedlongseed=1;returnseed=(seed*1103515245+12345)%32768;}無參函數(shù)頭部:intrandom()… 或者intrandom(void)…原型必須用intrandom(void);70典型應(yīng)用:隨機(jī)數(shù)生成函數(shù)。無參函數(shù)頭部:701、含義:寄存器是計算機(jī)CPU的重要組成部分,在c語言中允許將一些頻繁使用的變量存放在計算機(jī)的寄存器中,以節(jié)省運(yùn)算時間,提高效率.2、用法:用register說明。3、要點(diǎn):只有局部自動變量和形參可以作為寄存器變量,其它變量不允許。一個計算機(jī)系統(tǒng)中的寄存器數(shù)目是有限的,不能定義任意多個寄存器變量。不同系統(tǒng)對register變量的處理方法不同。如:MSC和TC對register只當(dāng)作自動變量處理。局部靜態(tài)變量不能定義為register變量。寄存器變量711、含義:寄存器是計算機(jī)CPU的重要組成部分,在c語言中允intfac(intn){

registerinti,f=1;for(i=1;i<=n;i++)f=f*i;returnf;}intmain(){inti;for(i=1;i<=5;i++)printf(“%d!=%d\n”,i,fac(i));return0;}72intfac(intn)72內(nèi)部函數(shù)與外部函數(shù)一、內(nèi)部函數(shù)格式:在函數(shù)定義時加上static.

static類型標(biāo)識符函數(shù)名(形參表)要點(diǎn):內(nèi)部函數(shù)又稱為靜態(tài)函數(shù),這樣的函數(shù)只限在所在的文件中.二、外部函數(shù)

格式:在函數(shù)定義時加上extern即:

extern類型標(biāo)識符函數(shù)名(形參表)要點(diǎn):函數(shù)被冠以extern說明函數(shù)為外部函數(shù),可以被其他文件中的函數(shù)所調(diào)用,當(dāng)一個函數(shù)在定義時,未說明static時隱含的類型為extern.73內(nèi)部函數(shù)與外部函數(shù)一、內(nèi)部函數(shù)二、外部函數(shù)73file1.cinta;/*外部變量定義*/externintpower();

/*外部函數(shù)說明*/intmain(){intb=3,c,d,m;printf(“enterthenumberaanditspower:\n”);scanf(“%d,%d:,&a,&m);c=a*b;printf(“%d*%d=%d\n”,a,b,c);d=power(m);printf(“%d**%d=%d\n”,a,m,d);}file2.cexterninta;/*外部變量說明*/intpower(n)

/*外部函數(shù)定義*/{inti,y=1;for(i=1;i<=n;i++)y*=a;return(y);return0;}74file1.cfile2.c741)從作用域角度看,main也是普通函數(shù),其中的定義是局部定義,作用域是main函數(shù)的體。2)復(fù)合語句里定義的變量,存在期是該復(fù)合語句的一次執(zhí)行。復(fù)合語句開始時創(chuàng)建,結(jié)束時撤消。復(fù)合語句再次執(zhí)行時重建,新變量與撤消的變量無關(guān),自動變量。for(n=0;n<10;n++){intm;if(n==0)m=2;/*循環(huán)第二次到這里時m的值未定*/}變量的幾個問題751)從作用域角度看,main也是普通函數(shù),其中的定義是局部定3)變量定義的嵌套函數(shù)定義只出現(xiàn)在全局作用域中,不可能嵌套。變量定義可出現(xiàn)在復(fù)合語句里,可能出現(xiàn)嵌套定義。規(guī)定:同一作用域里不允許定義多個同名變量。不同作用域中可以定義同名變量,不同作用域里定義的同名變量互不相干.例:intf(...){doublex,

n;....}intmain(){doublex,z;intn,m;....}763)變量定義的嵌套例:76嵌套作用域里可能出現(xiàn)同名變量定義,例:intf(intn){intx=2,y;....while(....){doublex=4;

x=x+1;....}

x=x+1;....}規(guī)定:內(nèi)層作用域里的同名變量定義(在此局部)遮蔽外層同名變量定義。77嵌套作用域里可能出現(xiàn)同名變量定義,例:77用關(guān)鍵字const定義的變量。是變量,但不允許賦值,只能初始化,其存在期中總代表同一個值:

constintnum=10;4)常變量若出現(xiàn)在局部作用域里,那么也動態(tài)建立和初始化,每次初始化的值可以不同:for(i=2;i<=200;i+=2){constintn=i*i;......}可用const定義常參數(shù),函數(shù)體里不能重新賦值。78用關(guān)鍵字const定義的變量。是變量,但不允許賦值,只能初始靜態(tài)動態(tài)存儲方式程序整個運(yùn)行期間函數(shù)調(diào)用開始至結(jié)束生存期編譯時賦初值,只賦一次每次函數(shù)調(diào)用時賦初值自動賦初值0或空字符不確定未賦初值靜態(tài)存儲區(qū)動態(tài)區(qū)存儲區(qū)寄存器局部變量外部變量作用域定義變量的函數(shù)或復(fù)合語句內(nèi)本文件其它文件局部變量默認(rèn)為auto型register型變量個數(shù)受限,且不能為long,double,float型局部static變量具有全局壽命和局部可見性局部static變量具有可繼承性extern不是變量定義,可擴(kuò)展外部變量作用域register局部staticauto外部static外部存儲類別變量存儲類型79靜態(tài)動態(tài)存儲方式程序整個運(yùn)行期間函數(shù)調(diào)用開始至結(jié)束生存期編譯作業(yè)1.讀程序?qū)懡Y(jié)果#include<stdio.h>intf1(int),f2(int);voidmain(){inti;for(i=2;i<5;i++)printf("f1(%d)=%d\t",i,f1(i));printf("\n");for(i=2;i<5;i++)printf("f2(%d)=%d\t",i,f2(i));printf("\n");}intf1(intx){intf=1;f*=x;returnf;}intf2(intx){staticintf=1;f*=x;returnf;}80作業(yè)1.讀程序?qū)懡Y(jié)果intf1(intx)80作業(yè)2.閱讀下列程序?qū)懡Y(jié)果#include<stdio.h>inta=3,b=5;intmax(inta,intb){intc;c=a>b?a:b;returnc;}voidmain(){inta=8;printf(“%d”,max(a,b));}81作業(yè)2.閱讀下列程序?qū)懡Y(jié)果#include<stdio.h>作業(yè)3:P173第10題f(x)=sin(x)-1/4*xf’(x)=cos(x)-1/4xn+1=xn-f(xn)/f’(xn)82作業(yè)3:P173第10題82Q&A!83Q&A!83

不為失敗找理由、要為成功找方法!84不為失敗找理由、要為成功找方法!1高級語言程序設(shè)計主講教師:賈彩燕計算機(jī)與信息技術(shù)學(xué)院計算機(jī)科學(xué)與技術(shù)系cyjia@85高級語言程序設(shè)計主講教師:賈彩燕2第五章

C程序結(jié)構(gòu)86第五章

C程序結(jié)構(gòu)3本章討論與C程序整體結(jié)構(gòu)有關(guān)的問題。對正確理解C語言/正確書寫C程序很重要。學(xué)習(xí)用C程序設(shè)計時應(yīng)了解的“深層問題”。1)基本數(shù)值類型的全面介紹2)函數(shù)與C程序結(jié)構(gòu),函數(shù)原型3)變量類,作用域與存在期4)預(yù)處理命令5)字位運(yùn)算符(特殊問題,初步了解,需要時深入)87本章討論與C程序整體結(jié)構(gòu)有關(guān)的問題。1)基本數(shù)值類型的全面介主要內(nèi)容數(shù)值類型函數(shù)和標(biāo)準(zhǔn)庫函數(shù)函數(shù)定義和程序的函數(shù)分解C程序結(jié)構(gòu)與變量預(yù)處理命令定義常量字位運(yùn)算符編程實(shí)例88主要內(nèi)容數(shù)值類型55.1數(shù)值類型實(shí)數(shù)類型:float,double,longdouble實(shí)數(shù)類型外的算術(shù)類型都是整數(shù)類型。字符類型也看作整數(shù)類型,可以作為整數(shù)參加運(yùn)算。每一基本整數(shù)類型都有帶符號與無符號兩種類型,用限定詞signed或unsigned說明。無符號類型的值大于等于0。同一基本類型的帶符號/無符號類型用同樣長度編碼。signed可省略,如signedlong簡寫為long。895.1數(shù)值類型實(shí)數(shù)類型:float,double,lon字符類型:char,signedchar,unsignedchar用一個字節(jié)表示,其中存字符編碼。ASCII字符集里數(shù)字(字母)字符的編碼連續(xù)排列。char等同于signedchar或unsignedchar(不同系統(tǒng)可能不同)。簡單程序只用char,不需要關(guān)心有無符號。只有用char參加整數(shù)運(yùn)算時才需要考慮?;続SCII字符集的編碼范圍是0-127。90字符類型:char,signedchar,unsigned整數(shù)類型

基本:int,shortint,longint總共六個: int unsignedint short unsignedshort long unsignedlongshortint簡寫為short,longint簡寫long,unsignedint簡寫為unsignedshort表示范圍不大于int,long不小于int。無符號/有符號類型位數(shù)相同。具體表示由C語言系統(tǒng)確定?;绢愋褪莍nt,一般用計算機(jī)的字長表示。16位機(jī)器的C系統(tǒng)中,int通常用16位表示;32位機(jī)器的C系統(tǒng)中,int通常用32位表示;91整數(shù)類型基本:int,shortint,longin整數(shù)常量可用十進(jìn)制八進(jìn)制(0開頭)十六進(jìn)制(0x或0X開頭)長整型加后綴L或lshort無常量寫法無符號數(shù)加后綴u或U123U,2987654LU,327LU,32014U無符號整數(shù)的算術(shù)運(yùn)算按取模方式做(不會溢出),超出表示范圍時取模作為計算結(jié)果。例:若16位unsignd范圍為0~65535。計算超范圍時取模65536。234U+65500U的計算結(jié)果是198U。92整數(shù)常量可用十進(jìn)制無符號整數(shù)的算術(shù)運(yùn)算按取模方式做(混合類型運(yùn)算前把小類型轉(zhuǎn)換到大類型的值。整數(shù)提升:小整數(shù)(short、char等)先轉(zhuǎn)為int值再運(yùn)算。若轉(zhuǎn)換結(jié)果超出int范圍(unsignedshort提升可能出問題),就提升為unsigned。基本類型相同時,認(rèn)為無符號類型是比同樣的有符號類型更大的類型。例如做下面計算:2365U+18764將先由18764(整型值)轉(zhuǎn)換生成unsigned對應(yīng)值,再用此新值參與運(yùn)算。93混合類型運(yùn)算前把小類型轉(zhuǎn)換到大類型的值。基本類型相同時,認(rèn)為基本數(shù)據(jù)類型的選擇C語言提供多個浮點(diǎn)類型和整數(shù)類型,供編程者選擇使用。如無特殊需要,浮點(diǎn)數(shù)總用double,因其精度和范圍能滿足一般要求(float精度過低,longdouble可能低效,一般不用)。如無特殊需要,整數(shù)總用是C語言里最基本的類型,能得到硬件基本支持,其效率不會低于任何其他整數(shù)類型。有時用long類型。如無特殊需要,字符總采用char。盡量少用unsigned類型,除非服務(wù)于特殊目的。94基本數(shù)據(jù)類型的選擇C語言提供多個浮點(diǎn)類型和整數(shù)類型,供編程主要內(nèi)容數(shù)值類型函數(shù)和標(biāo)準(zhǔn)庫函數(shù)函數(shù)定義和程序的函數(shù)分解C程序結(jié)構(gòu)與變量預(yù)處理命令定義常量字位運(yùn)算符編程實(shí)例95主要內(nèi)容數(shù)值類型12編寫大程序時應(yīng)特別注意函數(shù)分解。沒有合理函數(shù)分解不可能完成復(fù)雜工作/多花時間/程序更難理解/錯誤更難發(fā)現(xiàn)和糾正。開始就應(yīng)強(qiáng)調(diào)好的編程習(xí)慣(包括函數(shù)分解)。函數(shù)的作用:把一段計算抽象出來,封裝(包裝)成獨(dú)立實(shí)體。這種封裝程序段稱為函數(shù)定義。定義后通過函數(shù)名就可以用簡便方式要求執(zhí)行該函數(shù)所封裝的計算。這種描述片段稱為函數(shù)調(diào)用。5.2函數(shù)和標(biāo)準(zhǔn)函數(shù)庫問題復(fù)雜使程序變長。大程序難開發(fā)/難閱讀理解/難修改;修改時容易破壞完整性,難保證不引進(jìn)新錯誤。程序中常出現(xiàn)許多相同/類似片段。使程序更長,增加不同部分間的聯(lián)系,損害可修改性。96編寫大程序時應(yīng)特別注意函數(shù)分解。函數(shù)的作用:把一段計算抽象出基本C語言很小,ANSIC定義了標(biāo)準(zhǔn)庫,其中提供最常用的與平臺無關(guān)的功能。每個符合標(biāo)準(zhǔn)的C系統(tǒng)都提供了標(biāo)準(zhǔn)庫,通常還提供一些擴(kuò)充庫,以便使用特定硬件/特定系統(tǒng)的功能:DOS上的C系統(tǒng)提供與DOS有關(guān)的功能函數(shù)Windows上的系統(tǒng)提供與Windows有關(guān)的函數(shù)UNIX系統(tǒng)上的系統(tǒng)提供與UNIX接口的函數(shù)擴(kuò)充庫不標(biāo)準(zhǔn),使用擴(kuò)充庫的程序依賴于具體系統(tǒng)。庫函數(shù)實(shí)現(xiàn)常用計算,可按規(guī)定方式調(diào)用,不必自己實(shí)現(xiàn)/不必關(guān)心怎樣實(shí)現(xiàn)。開發(fā)一次使所有用戶受益。C語言的庫函數(shù)97基本C語言很小,ANSIC定義了標(biāo)準(zhǔn)庫,其中提供最常用的與標(biāo)準(zhǔn)庫功能包括

輸入輸出、文件操作、存儲管理,其他如數(shù)學(xué)函數(shù)、數(shù)據(jù)轉(zhuǎn)換函數(shù)等。有關(guān)介紹散布在各章,后面有詳細(xì)介紹。對具體C系統(tǒng)的擴(kuò)充庫可查閱系統(tǒng)聯(lián)機(jī)幫助,或查閱有關(guān)手冊、參考書籍。。下面介紹兩組常用標(biāo)準(zhǔn)函數(shù)。98標(biāo)準(zhǔn)庫功能包括下面介紹兩組常用標(biāo)準(zhǔn)函數(shù)。15字符分類(<ctype.h>)isalpha(c) c是字母字符isdigit(c)c是數(shù)字字符isalnum(c) c是字母或數(shù)字字符isspace(c) c是空格、制表符、換行符isupper(c) c是大寫字母islower(c) c是小寫字母iscntrl(c) c是控制字符isprint(c)c是可打印字符,包括空格isgraph(c) c是可打印字符,不包括空格isxdigit(c) c是十六進(jìn)制數(shù)字字符ispunct(c) c是標(biāo)點(diǎn)符號inttolower(intc) 轉(zhuǎn)為對應(yīng)小寫字母inttoupper(intc) 轉(zhuǎn)為對應(yīng)大寫字母是返回非零,不是返回零99字符分類(<ctype.h>)isalpha(c) #include<stdio.h>#include<ctype.h>intmain(){intc,cd=0,cu=0,cl=0;while((c=getchar())!=EOF){if(isdigit(c))++cd;if(isupper(c))++cu;if(islower(c))++cl;}

printf("digits:%d\n",cd);

printf("uppers:%d\n",cu);

printf("lowers:%d\n",cl);return0;}用標(biāo)準(zhǔn)庫函數(shù)完成判斷比自己寫條件更合適。

100#include<stdio.h>用標(biāo)準(zhǔn)庫函數(shù)完成判斷比自#include<stdio.h>#include<ctype.h>intmain(){intcount=0,c;while((c=getchar())!=EOF){if(isspace(c))continue;++count;while((c=getchar())!=EOF&&!isspace(c));}

printf("Words:%d\n",count);return0;}統(tǒng)計單詞程序:101#include<stdio.h>統(tǒng)計單詞程序:18隨機(jī)數(shù)生成函數(shù)程序調(diào)試:用數(shù)據(jù)做運(yùn)行試驗(yàn),隨機(jī)數(shù)據(jù)非常合適。計算機(jī)模擬:模擬實(shí)際情況/過程,客觀事物變化有隨機(jī)性。最常用的是除余定義:

a0=A an=(B×an-1+C)modDA,B,C,D為常數(shù),0≤A<D。適當(dāng)選擇B、C可產(chǎn)生0到D-1的較好隨機(jī)數(shù)列。計算機(jī)只能生成“偽隨機(jī)數(shù)”。常用方法是定義某種遞推關(guān)系,設(shè)法使序列中的數(shù)比較具有隨機(jī)性。102隨機(jī)數(shù)生成函數(shù)最常用的是除余定義:計算機(jī)只能生成“偽隨機(jī)數(shù)標(biāo)準(zhǔn)庫提供隨機(jī)數(shù)功能,需要包含文件<stdlib.h>。隨機(jī)數(shù)生成函數(shù):intrand(void)無參數(shù),得到0和符號常量

RAND_MAX

間的隨機(jī)整數(shù)。不同系統(tǒng)的RAND_MAX可能不同,至少為32767。函數(shù)srand用seed值設(shè)種子值:voidsrand(unsignedseed)默認(rèn)初始種子值是1;rand根據(jù)當(dāng)時種子值生成下一隨機(jī)數(shù)并修改種子值。103標(biāo)準(zhǔn)庫提供隨機(jī)數(shù)功能,需要包含文件<stdlib.h>。函數(shù)根據(jù)下面公式可以得到所需范圍內(nèi)的隨機(jī)數(shù):n=a+rand()%b其中a為位移,是所需連續(xù)整數(shù)范圍的第一個數(shù),b是比例因子,是所需連續(xù)整數(shù)范圍的寬度,則希望產(chǎn)生1--6之間隨機(jī)數(shù)的公式為:n=1+rand()%6希望產(chǎn)生0—1之間隨機(jī)數(shù)的公式為:n=rand()%2偽隨機(jī)數(shù)的產(chǎn)生

104根據(jù)下面公式可以得到所需范圍內(nèi)的隨機(jī)數(shù):偽隨機(jī)數(shù)的產(chǎn)生21例:編寫一個投擲骰子的程序,模擬10次,輸出每次投擲的點(diǎn)數(shù)。#include<stdio.h>#include<stdlib.h>intmain(){inti;printf(“\n”);

for(i=1;i<=10;i++)printf("%3d",1+rand()%6);return0;}結(jié)果:6655651153第二次運(yùn)行:6655651153使用srand函數(shù),通過提供不同的種子產(chǎn)生不同的隨機(jī)數(shù)序列。srand(x);

/*初始化隨機(jī)數(shù)發(fā)生器*/

unsignedx;

scanf(“%d”,&x);/*輸入一個非負(fù)的整數(shù)做種子*/161343565262333153565415161343565262105例:編寫一個投擲骰子的程序,模擬10次,輸出每次投擲的點(diǎn)數(shù)。#include<stdio.h>#include<stdlib.h>voidmain(){inti;printf(“\n”);

for(i=1;i<=10;i++)printf("%3d",1+rand()%6);}結(jié)果:3453314315再次運(yùn)行:4432355323

srand(time(NULL));/*使用time函數(shù)返回值做種子*/#include<time.h>例:編寫一個投擲骰子的程序,模擬10次,輸出每次投擲的點(diǎn)數(shù)106#include<stdio.h>結(jié)果:srand(主要內(nèi)容數(shù)值類型函數(shù)和標(biāo)準(zhǔn)庫函數(shù)函數(shù)定義和程序的函數(shù)分解C程序結(jié)構(gòu)與變量預(yù)處理命令定義常量字位運(yùn)算符編程實(shí)例107主要內(nèi)容數(shù)值類型245.3函數(shù)定義和程序的函數(shù)分解一個C程序主要是一系列的函數(shù)定義。函數(shù)定義形式:

函數(shù)頭部---

返回值類型函數(shù)名參數(shù)表

函數(shù)體庫函數(shù)有限,編寫復(fù)雜程序時需要自己定義函數(shù)。函數(shù)頭部:描述函數(shù)外部與函數(shù)內(nèi)部的聯(lián)系。

應(yīng)該總寫返回類型,無返回值用void說明。允許任意多個參數(shù),無參函數(shù)用(void)

(早期C語言對ANSIC的影響),定義無參函數(shù)時也可用()。1085.3函數(shù)定義和程序的函數(shù)分解一個C程序主要是一系列的函數(shù)主函數(shù)mainmain的返回值規(guī)定為int。這個返回值在程序結(jié)束時送給外部,程序外部(如操作系統(tǒng))可用這個值。一般返回0表示程序正常結(jié)束,其他值表示出錯main以外的函數(shù)只有被調(diào)用時才會執(zhí)行不允許調(diào)用mainintmain(){/*一般寫法*/......return0;}109主函數(shù)mainintmain()2611027程序的函數(shù)分解什么樣的程序片段應(yīng)該定義為函數(shù):重復(fù)出現(xiàn)的相同/相似計算片段,可設(shè)法抽取性定義為函數(shù)。長計算過程中有邏輯獨(dú)立性的片段,即使出現(xiàn)一次也可定義為函數(shù),以分解復(fù)雜性。經(jīng)驗(yàn)原則:可以定義為函數(shù)的內(nèi)容,就應(yīng)該定義為函數(shù);一個函數(shù)一般不超過一頁。往往存在很多可行的分解,尋找合理有效的分解是需要學(xué)習(xí)。111程序的函數(shù)分解什么樣的程序片段應(yīng)該定義為函數(shù):經(jīng)驗(yàn)原則:可以實(shí)例研究:字符圖形寫程序打印下面這類字符圖形最“簡單”的方式:用一系列putchar調(diào)用打印星號和空格(數(shù)清字符個數(shù),就可以寫出程序)。112實(shí)例研究:字符圖形寫程序打印下面這類字符圖形最“簡單”的方式方法二:程序里寫一系列printf調(diào)用。例:intmain(){/*打印菱形*/printf("*");printf("**");printf("***);....../*下略*/}不好!若要修改圖形大小或形式,程序需全部重寫如果需要畫出新圖形,已做工作對新工作毫無價值應(yīng)考慮畫這類圖形的“基本動作”,定義為函數(shù)。113方法二:程序里寫一系列printf調(diào)用。例:不好!若要修改圖分析:圖形由以下部分組成1)一段連續(xù)字符;2)在兩個特定位置的字符;字符圖形未必用星號,可推廣,引進(jìn)一個字符參數(shù)voidline(charc,intbegin,intend)voidpoints(charc,intfst,intsnd)

可考慮定義兩個函數(shù),其頭部分別為:

voidline(intbegin,intend)voidpoints(intfst,intsnd)line從begin到end輸出*

溫馨提示

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

最新文檔

評論

0/150

提交評論