C語言函數(shù)課件_第1頁
C語言函數(shù)課件_第2頁
C語言函數(shù)課件_第3頁
C語言函數(shù)課件_第4頁
C語言函數(shù)課件_第5頁
已閱讀5頁,還剩81頁未讀, 繼續(xù)免費閱讀

下載本文檔

版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領

文檔簡介

第7章函數(shù)教學目標掌握自定義函數(shù)的一般結構及函數(shù)的定義方法;掌握函數(shù)聲明、函數(shù)調用的一般方法;掌握形參、實參、函數(shù)原型等重要概念;熟悉數(shù)組作函數(shù)的參數(shù)時函數(shù)的定義和調用方法;熟悉函數(shù)嵌套、函數(shù)遞歸的概念;能定義和使用嵌套函數(shù)、遞歸函數(shù);了解局部變量、全局變量和變量的存儲類型的概念;熟悉auto型和static型局部變量的特點和用法。

Page1

第7章函數(shù)知識點函數(shù)的定義與調用;函數(shù)調用時的數(shù)據(jù)傳遞方法;數(shù)組作為函數(shù)參數(shù);函數(shù)的嵌套調用和遞歸調用;局部變量與全局變量的作用域;動態(tài)存儲變量和靜態(tài)存儲變量的生存期。重點:函數(shù)的定義與調用;函數(shù)調用時的數(shù)據(jù)傳遞方法。難點:函數(shù)調用時的數(shù)據(jù)傳遞方法;遞歸函數(shù)的設計;變量的作用域和生存期。

Page2

7.1函數(shù)概述函數(shù)是構成C程序的基本構件。C語言的程序是由一個主函數(shù)或若干個函數(shù)組成的。但編譯單位是源程序文件,而不是函數(shù)。C程序執(zhí)行是從main函數(shù)(主函數(shù))開始,在main函數(shù)中結束,不管main函數(shù)的位置如何。所有的函數(shù)獨立定義,main()函數(shù)可以調用任意其它函數(shù),其它函數(shù)之間可以相互調用,但任何函數(shù)都不能調用main()函數(shù)。

Page3

函數(shù)的分類標準函數(shù)(庫函數(shù)):由系統(tǒng)提供,如printf()自定義函數(shù):由用戶自己定義,解決特定的問題有參函數(shù):主調函數(shù)與被調函數(shù)之間有參數(shù)傳遞如printf()無參函數(shù):主調函數(shù)與被調函數(shù)之間無參數(shù)傳遞如getchar()有返回值函數(shù):被調函數(shù)返回一個值給主調函數(shù)如getchar()無返回值函數(shù):被調函數(shù)不帶回值給主調函數(shù)如printf()

Page4

7.2函數(shù)定義與函數(shù)調用函數(shù)定義:

函數(shù)調用:

函數(shù)定義時函數(shù)名后的括號中的變量叫形式參數(shù),簡稱形參

兩個實際參數(shù)函數(shù)調用時函數(shù)名后的括號中的參數(shù)叫實際參數(shù),簡稱實參

函數(shù)值兩個形式參數(shù)

Page5

一、函數(shù)定義與函數(shù)調用函數(shù)定義的格式:

[函數(shù)類型]函數(shù)名([形參及形參聲明表列]){內部變量定義和聲明部分執(zhí)行語句

}函數(shù)定義后,并不被執(zhí)行,只有當調用函數(shù)時,程序才轉到函數(shù)去執(zhí)行。函數(shù)調用的格式:函數(shù)名([實參表列])

Page6

1.無參無返回值函數(shù)的定義與調用#include<stdio.h>voidpstar(){ printf("****************\n");}voidmain(){inti;for(i=1;i<=10;i++)pstar();}函數(shù)類型void(“空類型”)表示無返回值

函數(shù)名無參數(shù)函數(shù)定義以語句方式調用無返回值函數(shù)函數(shù)定義

Page7

2.有參無返回值函數(shù)的定義與調用#include<stdio.h>voidpstar(intn){intk;/*形參在函數(shù)體內不能再定義*/for(k=1;k<=n;k++)printf("*");printf("\n");}voidmain(){inti;for(i=1;i<=10;i++)pstar(20);

}形參k

被聲明為int型

函數(shù)定義實參20

Page8

3.有返回值函數(shù)的定義與調用#include<stdio.h>intmax(intx,inty){intz;z=x>y?x:y;return(z);}voidmain(){inta,b,c;scanf("%d%d",&a,&b);c=max(a,b);/*將函數(shù)的返回值賦給變量c*/

printf("Maxis%d\n",c);

}int型函數(shù)(int

可缺省),表示函數(shù)返回值為整型

函數(shù)定義return后的括號可以不要

注意:程序可直接寫為:return(x>y?x:y);

Page9

有返回值函數(shù)的定義與調用上題程序可修改為:#include<stdio.h>intmax(intx,inty){return(x>y?x:y);}voidmain(){inta,b,c;scanf("%d%d",&a,&b);

printf(“Maxis%d\n”,max(a,b));

}將max函數(shù)的返回值作為printf函數(shù)的參數(shù)函數(shù)定義

Page10

二、函數(shù)的參數(shù)一、形式參數(shù)與實際參數(shù)對無參函數(shù),形參表列與實參表列均為空,但括號不能省略,如fun()。對有參函數(shù),實參與形參應個數(shù)相等,順序對應,類型一致或賦值相容。定義函數(shù)時形參不占用存儲單元,只有在調用函數(shù)期間才給形參分配存儲單元,并將實參的值傳遞給形參。函數(shù)調用結束,形參所占用存儲單元也被釋放。

Page11

函數(shù)的參數(shù)若形參是變量名,實參可以是常量、變量或表達式,如函數(shù)調用max(3,a+b);若形參是數(shù)組名,實參是數(shù)組名,或者數(shù)組指針。注:實參對形參的數(shù)據(jù)傳遞是“單向值傳遞”:實參的值傳遞給形參,而形參的值不會傳回給實參。

Page12

三、函數(shù)的返回值函數(shù)返回值的獲得:由return語句獲得。函數(shù)返回值的類型:取決于函數(shù)的類型。例:

floatmax(intx,inty){return(x>y?x:y);}

問:函數(shù)返回值是int還是float型?答:float將無返回值的函數(shù)類型定義為void。

Page13

四、函數(shù)的調用方式函數(shù)調用的格式:函數(shù)名([實參表列])函數(shù)調用的三種方式:函數(shù)語句:把函數(shù)調用作為一個語句,這種調用方式不使用函數(shù)的返回值,是無返回值函數(shù)的調用方式。

如,pstar(20);

Page14

函數(shù)的調用方式函數(shù)表達式:把函數(shù)調用作為表達式的一部分,這種調用方式使用函數(shù)返回的函數(shù)值,是有返回值函數(shù)的調用方式。

如,c=max(a,b);函數(shù)參數(shù):把函數(shù)調用作為一個實參進行函數(shù)調用,這種調用方式也要使用函數(shù)的返回函數(shù)值,也是有返回值函數(shù)的調用方式。

如,printf("Maxis%d\n",max(a,b));

Page15

舉例判斷素數(shù)函數(shù)1

(無返回值函數(shù))#include<stdio.h>#include<math.h>voidprime(intm){intj,k;k=sqrt(m);for(j=2;j<=k;j++)if(m%j==0)break;if(j>k)printf("%disaprimenumber\n",m);elseprintf("%disnotaprimenumber\n",m);}main(){intn;scanf("%d",&n);prime(n)}為了明確表示無返回值用void定義函數(shù)類型

Page16

舉例判斷素數(shù)函數(shù)2

(有返回值函數(shù))#include<stdio.h>#include<math.h>prime(intm){intj,k,f;k=sqrt(m);for(j=2;j<=k;j++)if(m%j==0)break;if(j>k)f=1;/*返回1表示m是素數(shù)*/elsef=0;/*返回0表示m不是素數(shù)*/return(f);}voidmain(){intn;scanf("%d",&n);if(prime(n)==1)printf(“%disaprimenumber\n",n);elseprintf("%disnotaprimenumber\n",n);}prime(n)

Page17

五、函數(shù)調用的條件1、被調函數(shù)是庫函數(shù)或已經存在的自定義函數(shù);2、若被調函數(shù)是庫函數(shù),一般需在文件開頭將其頭文件#include到本文件;

3、若被調函數(shù)是自定義函數(shù),一般應在調用前進行函數(shù)原型聲明,聲明的格式是:函數(shù)類型函數(shù)名(形參類型表列);或者:函數(shù)類型函數(shù)名(形參名及其類型表列);舉例:intmax(int,int);

或:intmax(intx,inty);

一個例外:若被調函數(shù)定義在前、調用在后,則可不加函數(shù)原型聲明。

Page18

函數(shù)原型聲明方式1、在主調函數(shù)內部聲明;2、在函數(shù)的外部聲明,一般放在所有函數(shù)定義之前,即文件開頭。

Page19

函數(shù)原型聲明舉例#include<stdio.h>voidmain(){inta,b;floatz;

scanf("%d%d",&a,&b);z=average(a,b);printf("a=%d,b=%d,c=%.2f\n",a,b,z);}floataverage(a,b)inta,b;{floatc;c=(a+b)/2.0;return(c);}函數(shù)調用在前

在主調函數(shù)內部聲明floataverage(int,int);函數(shù)定義在后

Page20

函數(shù)原型聲明舉例#include<stdio.h>

voidmain(){inta,b;floatz;scanf("%d%d",&a,&b);z=average(a,b);printf("a=%d,b=%d,c=%.2f\n",a,b,z);}floataverage(a,b)inta,b;{floatc;c=(a+b)/2.0;return(c);}函數(shù)調用在前

文件開頭,外部聲明floataverage(int,int);函數(shù)定義在后

Page21

函數(shù)原型聲明舉例#include<stdio.h>

floataverage(a,b)inta,b;{floatc;c=(a+b)/2.0;return(c);}voidmain(){inta,b;floatz;scanf("%d%d",&a,&b);z=average(a,b);printf("a=%d,b=%d,c=%.2f\n",a,b,z);}函數(shù)定義在前函數(shù)定義在前,函數(shù)調用在后;無需聲明函數(shù)調用在后

Page22

7.3函數(shù)調用中的參數(shù)傳遞簡單變量作為函數(shù)參數(shù)指針變量作為函數(shù)參數(shù)數(shù)組作為函數(shù)參數(shù)

Page23

1、簡單變量作為函數(shù)參數(shù)若形參是變量名,實參可以是常量、變量或表達式。實參對形參變量的傳遞是“單向數(shù)值傳遞”:實參的值傳遞給形參,而形參的值不會傳回給實參。改變形參的值不會使實參的值發(fā)生變化實參形參值

Page24

舉例對兩個數(shù)按降序排列(1)例:以下程序能實現(xiàn)a和b兩個變量的交換嗎?voidswap(intx,inty){intt;t=x;x=y;y=t;}#include<stdio.h>voidmain(){inta,b;scanf(”%d,%d”,&a,&b);if(a<b)swap(a,b);printf(”%d,%d\n”,a,b);}這樣的程序無法實現(xiàn)a和b兩個變量的交換!

35abxyt35353

Page25

2、指針變量作為函數(shù)參數(shù)指針作為函數(shù)參數(shù):

形參指針也指向實參指針所指的單元,于是改變形參指針所指單元的值,也就是改變實參指針所指單元的值。指針類型實參指針類型形參地址值

Page26

舉例對兩個數(shù)按降序排列(2)swap(int*p1,int*p2){intt;t=*p1;*p1=*p2;*p2=t;}#include<stdio.h>voidmain(){inta,b;int*pointer1,*pointer2;scanf(”%d,%d”,&a,&b);pointer1=&a;pointer2=&b;if(a<b)swap(pointer1,pointer2);printf(”%d,%d\n”,a,b);}若改變的是形參指針的值而不是形參指針所指單元的值,還能實現(xiàn)a和b兩個變量的交換嗎?

35……abp1p2t2000pointer1pointer220002002200220002002533

Page27

舉例對兩個數(shù)按降序排列(3)swap(int*p1,int*p2){int*t;t=p1;p1=p2;p2=t;}#include<stdio.h>voidmain(){inta,b;int*pointer1,*pointer2;scanf(”%d,%d”,&a,&b);

pointer1=&a;pointer2=&b;

if(a<b)swap(pointer1,pointer2);printf(”%d,%d\n”,a,b);}改變形參指針的值無法實現(xiàn)a和b兩個變量的交換!

35……abp1p2t2000pointer1pointer220002002200220002002200220002000

Page28

普通變量的指針作函數(shù)參數(shù)小結欲通過函數(shù)調用得到n個要改變的值,主調函數(shù):設置n個普通變量(a1,a2,……)存放n個要改變的值,并用n個指針變量(pa1,pa2,……)指向它們;被調函數(shù):設置n個指針變量(p1,p2,……)作為形參,函數(shù)體改變*p1,*p2,……的值;函數(shù)調用:主調函數(shù)以pa1,pa2,……為實參,將a1,a2,……的地址傳給形參p1,p2,……,于是,被調函數(shù)改變*p1,*p2,……的值實際上就是改變a1,a2,……的值。因此,函數(shù)調用結束,主調函數(shù)得到改變了的值。

Page29

3、數(shù)組作為函數(shù)參數(shù)

數(shù)組元素作為函數(shù)參數(shù)數(shù)組名作為函數(shù)參數(shù)

Page30

數(shù)組元素作為函數(shù)參數(shù)

例7.15:對應元素比較,如果數(shù)組a中的元素比數(shù)組b中元素大的次數(shù)多,則數(shù)組a大于數(shù)組b,反之數(shù)組b大于數(shù)組a,如果兩數(shù)組元素大于對方的元素次數(shù)相等,則兩數(shù)組相等。通過調用large函數(shù)實現(xiàn):

large(intx,inty){intflag;if(x>y)flag=1;elseif(x==y)flag=0;elseflag=-1;return(flag);}

Page31

舉例判斷兩個數(shù)值型數(shù)組的大小#include<stdio.h>voidmain(){inta[10],b[10],i,n=0,k=0;for(i=0;i<10;i++)scanf("%d",&a[i]);for(i=0;i<10;i++)scanf("%d",&b[i]);for(i=0;i<10;i++)

if(large(a[i],b[i])==1)n++;

elseif(large(a[i],b[i])==-1)k++;if(n>k)printf("aislargerthanb\n");

elseif(n<k)printf("bislargerthana\n");

elseprintf("aisequaltob\n");}數(shù)組元素a[i]、b[i]作實參

Page32

一維數(shù)組名作為函數(shù)參數(shù)形參接收實參傳遞的數(shù)組首地址,實際上,C編譯是將形參數(shù)組名作為指針變量來處理的。參數(shù)傳遞:地址值實參數(shù)組指針形參數(shù)組名或指針變量效果:函數(shù)調用期間,形參數(shù)組就是實參數(shù)組。一維數(shù)組名

一維數(shù)組名

一維數(shù)組指針一維數(shù)組指針變量實參

形參

Page33

一維數(shù)組名作參數(shù)使用說明實參數(shù)組與形參數(shù)組類型要一致。實參數(shù)組和形參數(shù)組大小可以不一致,也可以不指定形參數(shù)組第一維的大小,因為C編譯對形參數(shù)組第一維大小不做檢查,函數(shù)調用時不是把實參數(shù)組的值傳遞給形參數(shù)組,而是把實參數(shù)組的首地址傳遞給形參數(shù)組,于是形參數(shù)組結合到實參數(shù)組所占用的存儲空間。為方便編程,通常另設一參數(shù)用于傳遞數(shù)組元素的個數(shù)。

Page34

例7.17編寫函數(shù)統(tǒng)計一個一維數(shù)組(10個元素)中非0元素的個數(shù)。#include<stdio.h>intsolve(intb[10])/*一維數(shù)組名b作形參*/{intsum=0,i;for(i=0;i<10;i++)if(b[i]!=0)sum++;return(sum);} voidmain(){inta[10],num,i;for(i=0;i<10;i++)scanf("%d",&a[i]);num=solve(a);/*一維數(shù)組名a作實參*/printf("num=%d\n",num);}

Page35

例7.17編寫函數(shù)統(tǒng)計一個一維數(shù)組(10個元素)中非0元素的個數(shù)。#include<stdio.h>intsolve(intb[],intn)/*一維數(shù)組名b作形參*/{intsum=0,i;for(i=0;i<n;i++)if(b[i]!=0)sum++;return(sum);} voidmain(){inta[10],num,i;for(i=0;i<10;i++)scanf("%d",&a[i]);num=solve(a,10);/*一維數(shù)組名a作實參*/printf("num=%d\n",num);}一維形參數(shù)組的大小通常不指定,另設一參數(shù)用于傳遞數(shù)組元素的個數(shù)。

Page36

例:編寫函數(shù)將數(shù)組中n個元素按相反順序存放(1)voidinv(intx[],intn){intt,i,j,m=(n-1)/2;for(i=0;i<=m;i++){j=n-i-1;t=x[i];x[i]=x[j];x[j]=t;}}#include<stdio.h>voidmain(){inti,a[10]={3,7,9,11,0,6,7,5,4,2};printf("Theoriginalarray:\n");for(i=0;i<10;i++)printf("%d,",a[i]);printf("\n");

inv(a,10);

printf("Thearrayhasbeeninverted:\n");for(i=0;i<10;i++)printf("%d,",a[i]);}形參和實參均為一維數(shù)組

Page37

方法(2)形參為指針變量,實參為一維數(shù)組voidinv(int*x,intn)

{intt,*i,*j,m=(n-1)/2;for(i=x,j=x+n-1;i<=x+m;i++,j--){t=*i;*i=*j;*j=t;}}#include<stdio.h>voidmain(){inti,a[10]={3,7,9,11,0,6,7,5,4,2};printf("Theoriginalarray:\n");for(i=0;i<10;i++)printf("%d,",a[i]);printf("\n");

inv(a,10);

printf("Thearrayhasbeeninverted:\n");for(i=0;i<10;i++)printf("%d,",a[i]);}

Page38

方法(3)形參,實參均為指針變量

voidinv(int*x,intn)

{intt,*i,*j,m=(n-1)/2;for(i=x,j=x+n-1;i<=x+m;i++,j--){t=*i;*i=*j;*j=t;}}#include<stdio.h>voidmain(){inti,a[10]={3,7,9,11,0,6,7,5,4,2},*p;printf("Theoriginalarray:\n");for(i=0;i<10;i++)printf("%d,",a[i]);printf("\n");

p=a;inv(p,10);printf("Thearrayhasbeeninverted:\n");for(i=0;i<10;i++)printf("%d,",a[i]);}

Page39

方法(4)形參為一維數(shù)組,實參為指針變量voidinv(intx[],intn){intt,i,j,m=(n-1)/2;for(i=0;i<=m;i++){j=n-i-1;t=x[i];x[i]=x[j];x[j]=t;}}#include<stdio.h>voidmain(){inti,a[10]={3,7,9,11,0,6,7,5,4,2},*p;printf("Theoriginalarray:\n");for(i=0;i<10;i++)printf("%d,",a[i]);printf("\n");

p=a;inv(p,10);printf("Thearrayhasbeeninverted:\n");for(i=0;i<10;i++)printf("%d,",a[i]);}

Page40

折半(二分)查找折半查找法只能對有序數(shù)列進行查找,方法如下:假設n個數(shù)按由小到大的順序存放在數(shù)組a中,兩個位置指針top、bot分別指向查找范圍的頂部、底部。取查找范圍的中間位置mid=(top+mid)/2,將待查找的數(shù)x與a(mid)進行比較,將按以下三種結果分別處理:(1)x=a(mid):已找到,退出查找;

Page41

折半(二分)查找(2)x<a[mid]:x只可能落在top和mid-1范圍之內,將查找范圍的底部改為bot=mid-1,頂部top不變;(3)x>a[mid]:x只可能落在mid+1和bot范圍之內,將查找范圍的頂部改為top=mid+1,底部bot不變。確定新的查找范圍后,重復以上比較,直到找到或者top>bot,退出循環(huán)。top>bot表明嘗試過所有可能的范圍,但沒找到。

Page42

折半(二分)查找

x=65的查找過程下標數(shù)組元素第一次第二次第三次010←top123235341456←mid565←top←top←mid673←bot785←mid8979102←bot←bot

Page43

折半(二分)查找(數(shù)組從小到大)核心部分算法:top=0;bottom=n-1;result=-1;while((top<=bottom)&&(result==-1)){mid=(top+bottom)/2;/*取中間元素*/

if(a[mid]==x)/*所查找的數(shù)據(jù)是否是中間元素*/ result=mid;/*找到的位置*/

elseif(a[mid]<x) top=mid+1;elsebottom=mid-1;}

Page44

折半查找函數(shù)的定義

(數(shù)組從大到?。﹊ntBinarySearch(inta[],intn,intkey)/*key表示要找的數(shù)*/{inttop,bottom,mid;if(key>a[0]||key<a[n-1])return-1;/*返回-1表示沒找到*/else{top=0;bottom=n-1;while(top<=bottom){mid=(top+bottom)/2; /*取中間元素*/if(a[mid]==key)/*所查找的數(shù)據(jù)是否是中間元素*/ returnmid; /*返回找到的位置*/elseif(a[mid]>key) top=mid+1;elsebottom=mid-1;}return-1;}/*返回-1表示沒找到*/}

Page45

例7.24編寫一個字符串復制函數(shù)。#include<stdio.h>voidstringcopy(chars[],char*t){inti=0;while(*t!='\0'){s[i]=*t;i++;t++;}s[i]='\0';}voidmain(){charstr1[]="IloveBeijing!";char*str2="IloveChina!";stringcopy(str1,str2);printf("str1=%s\nstr2=%s\n",str1,str2);}

Page46

例7.25改用兩個字符指針變量作stringcopy函數(shù)的形參#include<stdio.h>voidstringcopy(char*p,char*q){while((*p++=*q++)!='\0');*p='\0';}voidmain(){charstr1[]="IloveBeijing!";char*str2="IloveChina!";stringcopy(str1,str2);printf("str1=%s\nstr2=%s\n",str1,str2);}

Page47

例7.26編寫一個求字符串長度函數(shù)#include<stdio.h>#include<string.h>intstringlen(chars[]){inti=0,len=0;while(s[i]!='\0'){len++;i++;}returnlen;}voidmain(){char*str;printf("Pleaseinputastring:");gets(str);printf("\nThestringlenthis%4d\n",stringlenth(str));}

Page48

多維數(shù)組名作函數(shù)參數(shù)例如:

floatmax(intarray[3][10])形參多維數(shù)組的第一維大小可以不指定

floatmax(intarray[][10])正確但是形參多維數(shù)組的第二維及其它高維的大小不能省略

floatmax(intarray[3][])錯誤

floatmax(intarray[][])錯誤

Page49

舉例求二維數(shù)組最大值函數(shù)的定義與調用例7.23#include<stdio.h>max_value(inta[][4]){inti,j,max;max=a[0][0];for(i=0;i<3;i++)for(j=0;j<4;j++)if(a[i][j]>max)max=a[i][j];return(max);}voidmain(){inta[3][4]={{1,3,5,7},{2,4,6,8},{15,17,34,12}};printf("max=%d\n",max_value(a));}/*形參二維數(shù)組的第一維大小可以不指定*/

Page50

7.4函數(shù)的嵌套調用和遞歸調用從什么地方調用函數(shù),就返回到什么地方...調用函數(shù)fun1...調用函數(shù)fun2main()函數(shù)fun2()函數(shù)fun1()函數(shù)①②⑤⑥⑦⑧⑨④③

Page51

函數(shù)的嵌套調用舉例—求cnm

voidmain(){intm,n,t;longc(int,int);scanf("%d%d",&m,&n);if(n>m){t=m;m=n;n=t;}printf("%ld\n",c(m,n));}longc(intm,intn){longf;longfac(int);f=fac(m)/(fac(n)*fac(m-n));return(f);}longfac(intt){inti;longs=1;for(i=1;i<=t;i++)s*=i;return(s);}在main函數(shù)中調用c函數(shù)在c函數(shù)中三次調用fac

函數(shù)

返回main函數(shù)返回c函數(shù)函數(shù)C:求cnm

函數(shù)fac:求t!

Page52

函數(shù)的遞歸調用inta(intn){intd,c;…d=a(c);

…}遞歸函數(shù)兩要素:1.遞歸調用

2.使遞歸結束的條件函數(shù)的遞歸調用:在定義一個函數(shù)的過程中又直接或間接地調用函數(shù)本身

Page53

函數(shù)的遞歸調用f函數(shù)調用f函數(shù)f2函數(shù)調用f1函數(shù)f1函數(shù)調用f2函數(shù)直接遞歸調用間接遞歸調用

Page54

遞歸函數(shù)舉例1—求階乘例7.31分析:1(n=0,1)fac(n)=n*fac(n-1)(n>1)floatfac(intn)/*求階乘函數(shù)*/{floatf;if(n==0||n==1)f=1;elsef=fac(n-1)*n;return(f);}#include<stdio.h>voidmain(){intn;scanf("%d",&n);if(n<0)printf("n<0,dataerror!");elseprintf("%d!=%15.0f\n",n,fac(n));}遞歸調用遞歸結束條件

Page55

遞歸函數(shù)舉例1—年齡問題例7.32分析:age(n-1)+2(n>1)age(n)=10(n=1)#include<stdio.h>age(intn){intc;if(n==1)c=10;elsec=age(n-1)+2;return(c);}voidmain(){printf("%d\n",age(5));}遞歸調用遞歸結束條件遞歸調用遞歸調用遞歸結束條件遞歸調用遞歸結束條件遞歸結束條件遞歸調用遞歸結束條件

Page56

遞歸函數(shù)舉例3#include<stdio.h>voidtry(){charc;if((c=getchar())!=’#’){try();putchar(c);}}voidmain(){try();}輸入apple#后的結果是:

elppa

Page57

7.5函數(shù)的返回值為指針一個函數(shù)可以返回整型、字符型、實型函數(shù)值,也可以返回一個指針值,即將地址作為函數(shù)值返回到主調函數(shù)中。返回指針的函數(shù)的定義:類型名*函數(shù)名(參數(shù)表){

函數(shù)體語句組

}

Page58

例7.34編寫一函數(shù),實現(xiàn)兩個字符串的連接,返回值為連接后字符串的首地址。#include<stdio.h>char*strcat(char*s1,char*s2)/*定義返回值是指針的函數(shù)*/{char*p=s1;while(*p!='\0')p++;while((*p++=*s2++)!='\0');*p='\0';returns1;}voidmain(){charstr1[30]="Ilearn",*str2="Clanguage.";char*s;s=strcat(str1,str2);/*strcat函數(shù)的返回值是指針*/printf("%s\n",s);}

Page59

例7.29編寫程序,使能從輸入的若干個字符串中找出最小的串,并將其輸出。#include<stdio.h>#include<string.h>intgetstring(charc[][81]){charlin[81],linnum=0;printf("Enterstringaspacestringtoend!\n");gets(lin);while(!strcmp(lin,"#")==0){strcpy(c[linnum],lin);linnum++;gets(lin);}returnlinnum;}/*返回字符串行數(shù)*/

Page60

接上頁char*findminstr(char(*s)[81],intnum)/*s是指向一維數(shù)組的指針*/{char*strq;inti;strq=s[0];for(i=1;i<num;i++)if(strcmp(s[i],strq)<0)/*尋找最小串*/ strq=s[i];returnstrq;}/*返回最小串的地址*/

Page61

接上頁voidmain(){charstr[50][81],*strp;intn,i;n=getstring(str);strp=findminstr(str,n);puts(strp);}

Page62

例7.29編寫程序,使能從輸入的若干個字符串中找出最小的串,并將其輸出。#include<stdio.h>#include<string.h>intgetstring(charc[][81]){charlin[81],linnum=0;printf("Enterstringaspacestringtoend!\n");gets(lin);while(!strcmp(lin,“#”)==0)/*輸入遇#號結束*/{strcpy(c[linnum],lin);linnum++;gets(lin);}returnlinnum;}/*返回字符串行數(shù)*/

Page63

接上頁char*findminstr(char(*s)[81],intnum)/*s是指向一維數(shù)組的指針*/{char*strq;inti;strq=s[0];for(i=1;i<num;i++)if(strcmp(s[i],strq)<0)/*尋找最小串*/ strq=s[i];returnstrq;}/*返回最小串的地址*/S[][81]

Page64

接上頁voidmain(){charstr[50][81],*strp;intn,i;n=getstring(str);strp=findminstr(str,n);puts(strp);}

Page65

7.6變量的作用域和存儲類別函數(shù)間數(shù)據(jù)傳遞的渠道:主調函數(shù)(普通變量參數(shù))被調函數(shù)主調函數(shù)(函數(shù)返回值)被調函數(shù)主調函數(shù)(數(shù)組參數(shù)/指針變量參數(shù))被調函數(shù)主調函數(shù)(全局變量)被調函數(shù)

Page66

局部變量#include<stdio.h>voidsub(int,int);voidmain(){inta=1,b=2;sub(a,b);printf("mainprogram%d%d\n",a,b);}voidsub(inta,intb){a=a+10;b=b+20;printf("subprogram%d%d\n",a,b);}程序結果:

subprogram1122mainprogram12

Page67

局部變量和全局變量變量按照其作用范圍分為局部變量和全局變量(外部變量)。

類別作用域

(有效范圍)局

量函數(shù)形參本函數(shù)在函數(shù)體首部定義的變量/數(shù)組本函數(shù)在復合語句首部定義的變量/數(shù)組本復合語句全局

變量在函數(shù)之外定義的變量/數(shù)組定義起至文件結束

Page68

局部變量和全局變量兩點說明:

①不同函數(shù)中的局部變量可以同名,全局變量與局部變量也可以同名,但它們代表不同的變量,在內存中占有不同的存儲空間。

②局部變量起作用時,同名全局變量不起作用。

Page69

局部變量和全局變量例7.41#include<stdio.h>inta=3,b=5;max(inta,intb){intc;c=a>b?a:b;return(c);}voidmain()

{inta=8;

printf("%d\n",max(a,b));}max()的局部變量a、bmax()的局部變量c實參a是main()的局部變量(8),實參b是全局變量(5)程序運行結果:8

使用max()的局部變量a、b

main()的局部變量a

全局變量a、b

Page70

全局變量intP1=1,P2=2;floatf1(inta){……}charc1,c2;floatf2(intb){……}voidmain(){……}全局變量P1,P2作用范圍全局變量c1,c2作用范圍一個不成文的約定:全局變量名的第一個字母大寫。

Page71

全局變量應用舉例例7.40有一個一維數(shù)組,內放10個學生的成績,寫一個函數(shù),求出平均分、最高分和最低分。#include<stdio.h>floatMax,Min;floataverage(floatarray[],intn){inti;floataver,sum=array[0];Max=Min=array[0];for(i=1;i<n;i++){if(array[i]>Max)Max=array[i];elseif(array[i]<Min)Min=array[i];

sum=sum+array[i];}aver=sum/n;return(aver);}全局變量能在定義之后的所有函數(shù)中使用

Page72

全局變量應用舉例voidmain(){floatave;floatscore[10],i;for(i=0;i<10;i++)scanf("%f",&score[i]);ave=average(score,10);printf("max=%6.2f\n",Max);printf("min=%6.2f\n",Min);printf("average=%6.2f\n",ave);}

Page73

變量的存儲類型局部變量按其生存的時間(生存期)劃分為動態(tài)存儲變量、靜態(tài)存儲變量和寄存器變量。變量定義完整格式:

[存儲類別]數(shù)據(jù)類型變量表列;存儲類別缺省為auto(自動型)

Page74

內存中用戶區(qū)存儲空間的分配

內存

系統(tǒng)區(qū)用戶區(qū)(存放用戶數(shù)據(jù)與程序)存放系統(tǒng)程序程序區(qū):程序靜態(tài)存儲區(qū):全局變量靜態(tài)局部變量動態(tài)存儲區(qū):自動局部變量形式參數(shù)函數(shù)調用時現(xiàn)場保護和返回值

Page75

變量的存儲類型動態(tài)變量靜態(tài)變量類別

存儲類別為auto(通常缺?。┑木植孔兞看鎯︻悇e為static的

局部變量存儲類別為register的局部變量所有類別的全局變量存儲

位置動態(tài)存儲區(qū)靜態(tài)存儲區(qū)寄存器生存期函數(shù)運行期間程序運行期間賦初值每調用函數(shù)一次,賦初值一次只在編譯時賦初值一次(數(shù)值型默認初值為0)(字符型默認初值為空字符)

Page76

局部靜態(tài)變量應用舉例1#include<stdio.h>f(inta){autointb=0;staticintc=3;

溫馨提示

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

評論

0/150

提交評論