一、函数 :使用函数前必须先定义或者声明
1、概念
一个C程序可由一个主函数和若干个其他函数构成。由主函数调用其他函数,其他函数也可以互相调用。同一个函数可以被一个或多个函数调用任意多次。
注:函数的使用顺序:
1) 在函数使用前,要定义这个函数,再使用。或者
2)先声明这个函数,再使用,最后要在代码的后面定义这个函数。例子如下(以无参函数为例)
第一种:先定义,再调用 void printstar() //定义printstar函数 { printf("*********************\n"); } void print_message() //定义print_message函数 { printf("How are you!\n"); } void main() { printstar(); //调用printstar函数 print_message(); //调用print_message函数 printstar(); }
第二种:先声明,再调用,再定义 int main() { void printstar(); //函数声明:对函数中用到的变量进行定义及对要调用的函数声明 void print_message();//函数声明 printstar(); //函数调用 print_message(); printstar(); return 0; } void printstar() //函数定义,返回值是void,代表不返回任何值 { printf("*********************\n"); } void print_message() { printf("How are you!\n"); }
说明:
1)C程序的执行是从main函数开始的。若在main中调用其他函数,在调用后流程返回到main函数,在main函数中结束整个程序的运行。
2) 所有函数都是平行的,即在函数定义时是分别进行的,不能进行嵌套定义。
3)函数间可以相互调用,但不能调用main函数。main函数是系统调用的。
4)从用户角度看,函数分标准函数和用户自定义函数。
①标准函数:即库函数,由系统提供。不同的c语言编译系统提供的库函数的数量和功能会有一些不同。
②用户自定义函数:用户自己定义的函数,用以解决用户专门需要的函数。
4)从函数形式看,函数分为有参函数和无参函数。
2、有参和无参函数
2.1 无参函数
类型标识符 函数名() { 声明部分; 语句部分; } eg:
void printstar() //void类型表示不需要带回函数值 { printf("*********************\n"); }
2.2 有参函数
类型标识符 函数名(形式参数表列)//“形式参数表列”即“形参” { 声明部分; 语句部分; } eg: int max(int x, int y) { int z; //函数体中的声明部分,对函数中用到的变量进行定义及对要调用的函数声明 z = x > y ? x : y; //语句部分 return(z); //将z的值作为函数值带回到主调函数中 }
注:函数定义时已指定max函数为整型,在函数体中要将函数体返回的值z定义为相同的类型。若返回值为整型时,在函数体已定义,那“类型标识符”处可省略定义,因为系统会默认为int型。
2.3 空函数
类型说明符 函数名() { } eg: void dummy() { }调用此函数时,什么工作也不做,没任何实际作用。在主调函数中写“dummy();”表明“这里要调用一个函数”,而现在这个函数没有用,等待以后扩充函数功能时补上。
3. 形式参数和实际参数
3.1 形参
在定义函数时函数名后面括号中的变量名称为“形式参数”
int max(int x, int y)
{
声明部分;
语句部分;
}
3.2 实参:调用函数时写的参数,实参可以是常量,也可以是变量
在调用函数时,参数名后面括号中的变量或表达式称为“实际参数”
c = max(a , b);
有参函数的调用 int max(int x, int y) //函数定义,这里的x,y是形参,形参一定是变量,一定要有数据类型 { int z; z = x > y ? x : y; return(z); } int main() { int a, b, c; scanf("%d%d", &a, &b); c = max(a, b); //函数调用,调用函数时写的参数,实参可以是常量,也可以是变量 printf("Max is %d\n",c); return 0; }
关于实参、形参的说明:
1)在定义函数中指定的形参,未出现函数调用时,其不占内存中的存储单元。只有发生函数调用时,函数max中的形参才被分配内存单元。调用结束后,形参所占的内存单元被释放。
2)实参可以是常量、变量或表达式,例如max(3,a + b);但要求它们有确定的值。
3)形参一定要是变量,不能是常量。定义函数时,必须指定形参的类型
4)实参与形参的类型应该相同或者赋值兼容。
5)在C语言中,只能由实参传向形参。调用结束后,形参存储单元被释放,实参单元仍保留并维持原来的值。
4、返回值
函数的返回值是通过函数中的return语句获得的。return语句将被调用函数中的一个确定值带回主调函数中去。
在main函数中调用exit和调用return的效果是一样的。但在子函数中调用exit代表整个程序退出了,但子函数中调用return只是这个子函数退出,程序还在运行。
二、多文件编译
2.1 头文件的使用
2.2 #include与#define的意义
2.2.1 #include
c语言中,#include就是简单的文件内容替换.下面是main.c的文件#include <stdio.h>
int max(int a, int b)
{
return (a > b) ? a : b;
}
int add(int a, int b)
{
return a + b;
}
int main()
{
int c = max(200, 300);
printf("c = %d\n", c);
c = add(15. 20);
printf("c = %d\n", c);
return 0;
}
可以创建内容为
#ifndef _AH_ //如果没有_AH_这个宏,就编译#endif之间的代码,若有就不编译 #define _AH_ //具体宏的名字是自定义的 //在#ifndef中的宏,为了避免和其他头文件中的宏冲突,一定要大写和下划线,必要时加数字,小写也行 int max(int a, int b); //函数声明 int add(int a, int b); #endif //加了define可以防止主函数中该头文件被多次include时,被重复预编译
的a.h文件表示函数声明,创建a.c文件表示函数
int max(int a, int b) { return (a > b) ? a : b; } int add(int a, int b) { return a + b; }在主函数中可以用
#include "a.h"
头文件代替该函数。
#include <stdio.h>
#inxlude “a.h”
int main()
{
int c = max(200, 300);
printf("c = %d\n", c);
c = add(15. 20);
printf("c = %d\n", c);
return 0;
}
2.2.2 #define
就是简单的文本替换。比如
#define NUM 20;//用MUN表示20
2.3 #ifndef与#endif
#ifndef的意思是条件预编译,若#ifndef后面的条件成立,那么就预编译从#ifndef开始到#endif间的代码,否则就不会去预编译这段代码#ifndef _AH_ //如果没有_AH_这个宏,就编译#endif之间的代码,若有就不编译 #define _AH_ //具体宏的名字是自定义的 int max(int a, int b); //函数声明 int add(int a, int b); #endif //加了define可以防止主函数中该头文件被多次include时,被重复预编译