内容正文:
《C语言程序设计》
(清华大学出版)
C 语言程序设计
第七章 函 数
2
第七章 函 数
第7章 函 数
7.1 函数定义和函数调用
7.2 函数的嵌套调用和递归调用
7.3 局部变量和全局变量
7.4 变量的存储类别
7.5 内部函数和外部函数
3
函数概述
程序设计有两大最高级的艺术
算法设计艺术
结构设计艺术
函数(function)是结构设计的最基本单位
“一个程序应该是轻灵自由的,它的子过程就象串在一根线上的珍珠。” ——Geoffrey James的《编程之道》
函数是C 语言的基本组成单元。每个函数用来完成某一特定的功能。
把单一功能做成函数的方式,有利于软件的复用。
第七章 函 数
4
函数概述
C程序的函数有两种:
标准库函数:由系统提供,如:sqrt(x), exp(x)。
自定义函数: 用户自定义函数
第七章 函 数
5
7.3 局部变量和全局变量
变量的分类
作用域: 变量的有效范围(空间)
局部变量
全局变量
生存期: 变量存在的时间(时间)
静态变量: 从程序开始执行到程序结束
动态变量: 从包含该变量定义的函数开始执行至函数执行结束
第七章 函 数
6
7.3.1 局部变量(内部变量)
定义:在函数内定义的变量。
作用域:在本函数内有效。
说明:
(1) main函数中定义的变量只在
main函数中有效。
(2) 形参属于局部变量。
(3) 不同函数中同名变量,占不同内
存单元。
(4) 在复合语句中定义的变量,只在
本复合语句中有效。
7.3 局部变量和全局变量
void main()
{ int a,b,c;
a=1;b=2;
c=a+b;
{ int c;
c=a-b;
printf("%d
",c);
}
printf("%d
",c);
}
输出:
-1
3
第七章 函 数
7
7.3.2 全局变量
(外部变量)
定义:在函数外部定义的变量。
作用域:从定义的位置到本文件结束。
7.3 局部变量和全局变量
x, i, j
a,b,c,d
m, n
c1,c2
a1, a2
int a1=1,a2=5;
float f1(float x)
{ int i,j;
... ...
}
char c1,c2;
char f2(int a, int b)
{int c,d;
... ...
}
void main()
{int m,n;
... ...
}
第七章 函 数
8
注意:
(1) 设置全局变量的作用是增加了函数间数据传递的通道。
(2) 全局变量定义时未初始化,系统为其赋初值0。
(3) 若全局变量与局部变量同名,则在局部变量的作用范围内,同名的全局变量不起作用。
7.3 局部变量和全局变量
【例7.10】编写函数求两个数的和与积。
#include <stdio.h>
float add, mult;
void func(float x, float y)
{ add=x+y;
mult=x*y;
}
void main()
{ float a,b;
scanf("%f%f", &a,&b);
func(a,b);
printf("%.2f %.2f
",add,mult);
}
运行情况如下:
3 8↙
11.00 24.00
第七章 函 数
9
注意:
(4) 当全局变量定义在后,引用在前时,应在引用它的函数中用extern 对此全局变量进行声明(说明)。
7.3 局部变量和全局变量
【例7.11】用extern声明外部变量,扩展它在程序文件中的作用域
#include<stdio.h>
int max(int x, int y)
{ int z;
z=x>y?x:y;
return(z);
}
void main(){
extern A, B;
printf("%d", max(A, B));
}
int A=8, B=2;
第七章 函 数
10
(5) 当一个程序由多个源文件组成时,如果想在一个文件中引用另一个文件中的已定义的外部变量,要用extern对该变量进行声明。
文件a1.c中的内容为:
#include <stdio.h>
int a;
main()
{ int power(int);
int d,m;
printf("enter a number
and its power :
");
scanf("%d,%d", &a, &m);
d=power(m);
printf("%d**%d=%d",a,m,d);
}
文件a2.c中的内容为:
extern a;
int power(int n)
{ int i,y=1;
for(i=1;i<=n;i++)
y*=a;
return(y);
}
【例7.12】用extern将外部变量的作用域扩展到其他文件。
第七章 函 数
11
int x=1,y=2;
void sub(int y)
{
x++; y++;
printf(“(1) x=%d,y=%d
”,x,y);
}
void main()
{ int x = 5;
sub(x);
printf(“(2) x=%d,y=%d
”,x,y);
}
练习:
程序结果
(1) x=2,y=6
(2) x=5,y=2
第七章 函 数
12
#include<stdio.h>
int m=10,n=100;
void de( )
{ int n=100;
n-=20;
m-=2; }
main( )
{ int n=80;
for(; n>=60;)
{ de( );
n=n-20;
printf(“%d
”,n+m);
}
}
de( )函数中局部变量n的作用域
main()中局部变量n的作用域
全局 变量m , n
的作用域
运行结果:
68
46
全局变量可以与局部变量同名。在局部变量的作用范围内,全局变量不起作用。
第七章 函 数
13
7.4 变量的存储类型
变量的属性: int x;
数据类型:如 int, float 等。
存储类型:是指数据在内
存中的存储方式。
分两大类:静态存储类
动态存储类
用户内存空间
静态存储区
动态存储区
程序区
具体包括四种:自动的(auto), 静态的(static),
寄存器的(register) ,外部的(extern)。
变量定义的形式:存储类型标识符 类型标识符 变量名;
例如: auto int x;
或 int x;
第七章 函 数
14
7.4 变量的存储类型
auto 自动变量——动态存储区
register 寄存器变量 ——CPU中的寄存器
extern 外部变量 ——静态存储区
static 静态变量——静态存储区
存储类型
程序区
静态存储区
动态存储区
形参、自动变量、函数调用的现场等
全局变量、静态变量
存放数据
第七章 函 数
15
7.4 变量的存储类型
局部变量的存储方式(三种)
自动变量
静态局部变量
寄存器变量
第七章 函 数
16
1、自动变量 (auto )
“自动”体现在
进入语句块时自动申请内存,退出时自动释放内存
对它们分配和释放存储空间的工作由编译系统自动处理,故称其为自动变量
标准定义格式
auto 类型名 变量名;
动态局部变量
缺省的存储类型
不初始化时,值是不确定的
例如:
int f ( int a ) /* 形参a为自动变量, auto省略 */
{ auto int b,c=3; /*定义b,c为自动变量*/
……}
第七章 函 数
17
2、静态局部变量
有时希望函数中局部变量的值在函数调用结束后不消失(以后一直存在,并总是保持它的最新值,即具有记忆性。)即不释放存储单元。此时可指定该变量为“静态局部变量”,用关键字“static”说明。
静态局部变量系统自动初始化为0。存放在静态存储区中
第七章 函 数
18
2、静态局部变量
有时希望函数中局部变量的值在函数调用结束后不消失(以后一直存在,并总是保持它的最新值,即具有记忆性。)即不释放存储单元。此时可指定该变量为“静态局部变量”,用关键字“static”说明。
静态局部变量系统自动初始化为0。存放在静态存储区中
静态变量和全局变量都是静态存储类型
自动初始化为0
从静态存储区分配,生存期为整个程序运行期间
但作用域不同
第七章 函 数
19
【例7.13】考察静态局部变量的值
#include<stdio.h>
int func(int a)
{int b=0;
static int c = 1;
b = b + 1;
c = c + 1;
return( a + b + c );
}
void main()
{int a = 2,i;
for(i= 0;i<3;i++) printf(" %d",func(a));
}
分析:i=0时:
a: 2
b:0
c:1
b:1
c:2
a+b+c=2+1+2=5;
运行结果: 5 6 7
分析:i=1时:
a: 2
b:0
c:2
b:1
c:3
a+b+c=2+1+3=6;
第七章 函 数
20
3、寄存器变量(register)
对频繁使用的变量,为减少存取变量花费的时间,C语言允许将局部变量的值存放在CPU运算器的寄存器中,称为“寄存器变量”,用关键字“register”说明。
说明:
寄存器变量的类型一般只限于整型、字符型或指向整型、字符型的指针,且只用于局部变量和形参。因此,全局寄存器变量是非法的。
不能定义任意多个寄存器变量,因为一个计算机系统中寄存器的数目是有限的。
不能取寄存器变量的地址
第七章 函 数
21
7.5 内部函数和外部函数
1. 内部函数
内部函数 只能被本文件中的其他函数所调用。
在定义函数时,在前面加 static
即:
static 类型标识符 函数名(形参表)
例如:
static float fun(float x, float y)
{
……
}
第七章 函 数
22
7.5 内部函数和外部函数
2. 外部函数
(1) 在定义函数时,在前面加上 extern,则表示该函数为外部函数,可供 其他文件 调用。 如
extern float fun(float x, float y) { … … }
或
float fun(float x, float y) { … … }
(2) 在需要调用此函数的文件中,用extern 声明所用函数是外部函数。如
extern float fun(float x, float y);
或
float fun(float x, float y);
第七章 函 数
23
练习: f ( int a )
{ auto int b=0;
static int c=3; /*定义静态局部变量c*/
b=b+1;
c=c+1;
return(a+b+c); }
main()
{ int a=2,i;
for( i =0;i <3;i++)
printf(“%d”,f(a)); }
运行结果为:
7 8 9
第七章 函 数
24
int k=0;
void fun(int m)
{ m+=k; k+=m;
printf(“m=%d k=%d”,m,k++);
}
main()
{ int i=4;
fun(i++);
printf(“i=%d k=%d
”,i,k);
}
输出结果:
m=4 k=4
i=5 k=5
第七章 函 数
25
int a=4;
int f(int n)
{ int t=0;
static int a=5;
if (n%2) {int a=6; t+=a++;}
else {int a=7;t+=a++;}
return t+a++;
}
main()
{ int s=a, i=0;
for( ;i<2;i++) s+=f(i);
printf(“%d
”,s);
}
A) 24 B) 28 C) 32 D) 36
答案:B
第七章 函 数
26
THANK YOU
main�
f1�
f2�
f3�
f4�
f5�
f6�
f7�
$$