版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領
文檔簡介
1、C語言程序設計,Lec 4 函數,.,2,引言,例:求一些圓盤的面積,圓盤半徑分別為: 3.24、2.13、0.865、3.746、12.3364、8.421,/設圓周率為 3.1416,可寫出下面程序: #include int main () printf(radius:%f, area:%fn, 3.24, 3.24 * 3.24 * 3.1416); printf(radius:%f, area:%fn, 2.13, 2.13 * 2.12 * 3.1415); ,繁瑣的東西很容易弄錯,不易修改,標準函數有限,需求無限。,.,3,引言,如果有求圓面積的函數double c_area(d
2、ouble r) 如果有打印圓面積的函數 pc_area(double r),int main () printf(radius:%f, area:%fn, 3.24, c_area(3.24) ); printf(radius:%f, area:%fn, 2.13, c_area(2.13) ); ,函數能使程序變短, 變得易寫/易理解/易修改,int main () pc_area(3.24); pc_area(2.13); ,.,4,引言,半徑3.24高2.4的圓錐體積: 外半徑5.3,內半徑3.07,高4.2的空心圓柱體積:,2.4 * c_area( 3.24 ) / 3.0,( c
3、_area(5.3) - c_area(3.07) )*4.2,.,5,目標,學會把常用的代碼定義為函數 學會在程序中使用函數 掌握C語言提供的常用庫函數 了解遞歸的基本原理,.,6,主要內容,函數定義 函數調用 C語言常用函數 函數與遞歸 變量作用域,.,7,4.1 函數定義,將實現某個功能的代碼變成函數,.,8,函數定義,把一段計算定義成函數并給以命名,定義后就可以在任何需要的地方通過名字調用。,/定義函數 c_area 的程序片段: double c_area (double r) return r * r * 3.1416; ,9,定義函數的要素,函數頭 函數名:使用函數需要的名稱,合
4、法標識符 返回值類型函數計算結果的數據類型 參數表完成計算需要的數據(數量和類型) 函數體,實現函數功能的代碼, 由一對大括號包圍,.,10,函數返回值,函數返回值表示函數內代碼計算的結果 一個函數最多只能有一個返回值,返回值通常是計算結果或者表示計算狀態(tài)的信息,由調用者使用 如果函數有返回值函數必須指定返回值類型,如果函數不需要返回值必須使用void作為函數返回值類型。 函數返回值通過return語句返回,return語句一旦執(zhí)行,整個函數就結束。,.,11,函數返回值,一個函數中可以有多條return語句,但只會執(zhí)行其中一條。 return語句形式:return 表達式; return語句
5、中表達式求值的類型應該和函數返回值類型一致,如果不一致會自動進行類型轉換 返回值類型為void時,不需要return語句或者寫成return;,12,函數定義示例,void pc_area(double r) printf(r = %f, S = %fn, r, 3.14159265 * r * r); ,double c_area (double r) return r * r * 3.1416; ,int max(int a, int b) if(ab) return a; return b; ,int compare( int x, int y ) if( x = y ) return
6、0; else if( x y ) return 1; else return -1; ,13,關于return語句,double c_area (double r) return r * r * 3.1416; int main() double v=2.4 * c_area( 3.24 ) / 3.0; printf(v=%fn,v); ,int main() double s = c_area( 3.24 ); double v=2.4 * s / 3.0; printf(v=%fn,v); ,需要注意返回值類型為void的函數不能放在表達式中參與運算,.,14,函數參數表,函數可以有0
7、個或多個參數,這些參數稱為形式參數 每個參數必須指明類型和參數名稱 函數參數是函數內的局部變量,只在函數體內有效 函數參數只有在函數被調用時才有效 函數參數的初始值由調用者傳入(通過實際參數以值拷貝的方式傳入),.,15,形參和實參,形參:在函數定義中括號內的標識符,與函數調用時的實參一一對應 實參:在調用函數的括號中使用的表達式,它的值被傳入函數并賦值給函數的對應形參。,.,16,形參和實參,#include /定義函數 double c_area (double r ) return r * r * 3.1416; int main () double v,radius=3.24; /調用
8、函數 v=2.4 * c_area( radius ) / 3.0; return 0; ,形參,實參,.,17,函數定義不能嵌套,#include #include double c_area (double r) return pow(r, 2) * 3.1416; int main () double v; v=2.4 * c_area( 3.24 ) / 3.0; return 0; ,#include #include int main () double c_area (double r) return pow(r, 2) * 3.1416; double v; v=2.4 * c
9、_area( 3.24 ) / 3.0; return 0; ,.,18,4.2 函數調用,.,19,調用系統(tǒng)函數,包含必要的頭文件,其本質是將函數原型添加到程序中 在需要的地方使用函數,傳入類型和數量正確的實際參數,函數返回值可以作為表達式的一部分,#include #include int main() double sum=0; int n=1; while(n=100) sum=sum+ sin(1.0/n) ; n=n+1; printf(sum=%fn,sum); return 0; ,函數原型就是函數頭部加上分號, 其作用是告訴編譯器函數應該以什么形式調用,.,20,調用自定義函
10、數,方法1(函數定義放在調用函數之前): 在需要的地方使用函數,傳入類型和數量正確的實際參數,函數返回值可以作為表達式的一部分,#include /c_area函數在調用前定義 double c_area (double r) return r * r * 3.1416; int main () double v; printf(radius:%f, area:%fn, 3.24, c_area(3.24) ); v=2.4 * c_area( 3.24 ) / 3.0; return 0; ,.,21,調用自定義函數,方法2(函數定義放在調用函數之后): 在函數調用之前給出函數原型 在需要的
11、地方使用函數,傳入類型和數量正確的實際參數,函數返回值可以作為表達式的一部分,#include /函數原型在調用之前 double c_area (double r); int main () double v; printf(radius:%f, area:%fn, 3.24, c_area(3.24) ); v=2.4 * c_area( 3.24 ) / 3.0; return 0; /函數定義在調用之后 double c_area (double r) return r * r * 3.1416; ,.,22,函數調用的若干問題,C語言是一個函數式語言,所有可執(zhí)行語句都必須放在某個函數
12、體內 調用函數的函數稱為主調函數,被調用的函數稱為被調函數 當函數調用發(fā)生時,主調函數暫停,程序控制轉入被調函數,被調函數執(zhí)行結束后,主調函數繼續(xù),.,23,函數調用的若干問題,#include #include double c_area (double r) return pow(r, 2) * 3.1416; int main () double v; v=2.4 * c_area( 3.24 ) / 3.0; return 0; ,.,24,參數傳遞機制,形式參數在函數調用時才分配存儲空間,并接受實際參數的值 實際參數可以為復雜的表達式,在函數調用前獲得計算 形式參數與實際參數可同名,
13、也可不同名,.,25,參數傳遞機制,參數較多時,實際參數值逐一賦值,它們必須保持數目、類型、順序的一致 參數的賦值過程單向不可逆,函數內部對形式參數值的修改不會反映到實際參數中 函數參數一般為函數輸入集的一部分,函數輸出集一般使用返回值表示,只有使用特殊的手段(指針/數組)才可以將函數參數作為函數輸出集的一部分,.,26,參數傳遞機制,void swap( int a, int b ) int t; t = a; a = b; b = t; ,int main() int a=5, b=3; printf( before swap: a= %d; b= %dn, a, b ); swap(a,
14、 b); printf( after swap: a= %d; b=%dn, a, b ); return 0; ,swap函數中的a和b與main函數中的a和b是什么關系? 兩個printf輸出的結果是什么?,swap函數數據區(qū),main函數數據區(qū),void swap( int a, int b ) int t; / 2 t = a; a = b; b = t; / 3 ,int main() int a=5, b=3; / 1 swap(a, b); / 4 return 0; ,.,28,函數示例,1. 請寫一個程序,給出指定整數范圍1,10000內的所有完數。判斷是不是完數用一個函數完
15、成。,int isPerfectNumber(int n) int i; for(i=1,sum=0;i=n/2;i+) if(n%i=0) sum+=i; return sum=n; ,.,29,函數示例,2. 寫一個函數求兩個整數的最大公約數,int gcd( int m, int n) int i; int min=m1;i-) if(m%i=0 ,.,30,函數示例,3. 寫一個函數判斷一個數是不是素數,用函數返回值表示判斷結果(非0表示是素數,0 表示不是素數),int isPrime(int n) int i, isprime=1; for(i=2; in; i+) if(n%i=
16、0) isprime=0; break; return i=n; ,.,31,課堂練習,寫一個函數判斷傳入的整數n(100n=1 返回值表示正確轉換并賦值的字段數,經常用來判斷輸入格式是否正確,.,41,scanf返回值示例(scanf.c),#include int main() int n=0; int a=0,b=0; n=scanf(%d %d, ,輸入1: 3 4,輸入2: 3 4.5,輸入3: 3 a,輸出1: n=2 a=3 b=4,輸出2: n=2 a=3 b=4,輸出1: n=1 a=3 b=0,.,42,輸入輸出函數,int getchar()從標準輸入流(stdin)讀取
17、一個字符 緩沖輸入,需要按下回車后才能獲取到值 正常情況下,返回值表示讀入的字符 如果返回值是EOF(-1)表示讀錯誤或到了流結束位置 int putchar(int ch)將字符ch寫入標準輸出流(stdout) 示例:將輸入的一行小寫字符轉換成大寫字符。(chario.c),.,43,時間函數,#include time_t time(time_t *timer)獲得從1970/1/1至今的秒數 time_t可以看作整數類型 clock_t clock();獲得從程序開始運行至今處理器經過的時鐘數 clock_t可以看作整數類型 CLOCKS_PER_SEC表示每秒有多少個時鐘的常數,.,
18、44,時間函數(time.c),#include #include int main() int start,finish; double time; start=clock(); . finish=clock(); time=(finish-start)*1.0/CLOCKS_PER_SEC; . return 0; ,對這一段程序計時,.,45,隨機數函數,#include int rand()產生一個0,RAND_MAX范圍內的偽隨機數 RAND_MAX是一個系統(tǒng)常數,可以直接使用 void srand( unsigned int seed )設置偽隨機數序列的種子 如果不設定隨機數系列
19、的種子,同一個程序兩次運行得到的隨機數完全相同 通常以時間作為隨機數種子,.,46,隨機數函數,產生5個隨機數(rand1.c),#include #include int main() int i; printf( RAND_MAX is %d.n, RAND_MAX ); printf( Five numbers generated as follows:n ); for( i = 0; i 5; i+ ) printf( “%d , rand() ); printf( n ); return 0; ,.,47,隨機函數,用時間做種子產生5個隨機數(rand2.c),#include #i
20、nclude #include int main() int i; printf( Five numbers generated as follows:n ); srand( (int)time(NULL) ); for( i = 0; i 5; i+ ) printf( %d; , rand() ); printf( n ); return 0; ,.,48,隨機函數,生成5個low,high范圍內的隨機數(rand3.c),#include #include #include int main() int i, low=10, high=20; srand( (int)time(NULL)
21、 ); for( i = 0; i 1,考慮 n 1 個圓盤,如果能將 n - 1 個圓盤移動到某個塔座上,則可以移動第 n 個圓盤 策略:首先將 n 1 個圓盤移動到塔座 Y 上,然后將第 n 個圓盤移動到 Z 上,最后再將 n - 1 個圓盤從 Y 上移動到 Z 上,.,58,漢諾塔(hanoi)問題,void MoveHanoi( unsigned int n, /圓盤數量 char from, /起始位置 char tmp, /中轉位置 char to ) /目標位置 if( n = 1 ) /遞歸結束條件 將圓盤1從 from 移動到 to else 將 n 1 個圓盤從 from
22、以 to 為中轉移動到 tmp; /遞歸 將圓盤 n 從 from 移動到 to 將 n - 1個圓盤從 tmp 以 from 為中轉移動到 to; /遞歸 ,.,59,遞歸的缺點,函數調用需要額外的空間(棧)來完成,在調用次數很多的情況下會降低程序效率 遞歸調用中的重復計算,.,60,Fibonacci數列的兩種求解方法(fib.c),/使用遞歸求Fibonacci數列 int fib_recursion(int n) if(n=0 | n=1) return 1; return fib_recursion(n-1) + fib_recursion(n-2); ,/使用循環(huán)求Fibonacci數列 int fib_loop(int n) int fn,fn_1=1,fn_2=1,i; if(n=0|n=1) return 1; for(i=2;i=n;i+) fn=fn_1+fn_2; /計算f(n) fn_2=fn_1; /更新f(n-2) fn_1=fn; /更新f(n-1) return fn; ,遞歸到循環(huán)的轉換常常需要借助于高級的程序設計技術和一定的數據結構才能完成,61,兔子繁殖問題( Fibonacci數列),假設有一對兔子,一個月后成長為大兔子,從第二個月開始,每對大兔子生一對小兔子。不考慮兔子的死亡,求第n個月的兔子總數,.,62,
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
- 4. 未經權益所有人同意不得將文件中的內容挪作商業(yè)或盈利用途。
- 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
- 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 2025年市場營銷策劃執(zhí)行規(guī)范
- 神木化工管理流程
- 物業(yè)管理投訴處理流程與規(guī)范
- 單位安全責任制度
- 超市商品質量及售后服務制度
- 采購物資供應商評價與淘汰制度
- 辦公室員工出差安全管理制度
- 2026年鄒平城投集團招聘備考題庫含答案詳解
- 關于2025年下半年沐川縣中等職業(yè)學校公開考核招聘急需緊缺專業(yè)技術人員的備考題庫及一套完整答案詳解
- 養(yǎng)老院安全管理制度
- 浙江省湖州市2024-2025學年高二上學期期末考試語文試題(解析版)
- T/CNESA 1001-2019電力儲能用直流動力連接器通用技術要求
- DB31/T 1402-2023養(yǎng)老機構認知障礙照護單元設置和服務要求
- GB/T 24217-2025洗油
- (人教2024版)英語七下全冊新教材解讀課件(分單元)
- 寧波海上風電項目可行性研究報告
- 小學生急救心肺復蘇知識科普
- 肩周炎中醫(yī)診療指南
- 旅游學概論(李天元)課件
- 《審計學》全套課件
- 2024年抖音影視作品宣傳合同
評論
0/150
提交評論