“先生,不是在这种环境下。因此我也被编写了三十多个辅助功能——”
——C3PO,在被粗鲁打断之前,报告一个并不出色的额外功能数量,《星球大战》剧本
和你熟悉的其他语言非常类似,C 语言也有函数(functions)的概念。
函数可以接受各种参数(arguments),并返回一个值。不过有一点很重要:参数和返回值的类型是预先声明的——因为 C 就是这样喜欢的!
我们来看一个函数示例。这个函数接受一个 int 作为参数,并返回一个 int。
#include <stdio.h>
int plus_one(int n) // 这是函数的“定义”
{
return n + 1;
}
函数名前的 int 表示返回值类型。
int n 表示这个函数接收一个 int 类型的参数,存储在名为 n 的参数变量中。参数是局部变量的一种特殊类型,函数调用时会将传入的值复制给它。
我要强调的一点是,参数是被复制到形参中的。只要明白形参是实参的一个副本,而不是实参本身,许多 C 语言的概念就更容易理解。稍后会详细讲解这个内容。
继续看程序中的 main() 函数,我们可以看到对函数的调用,并且将返回值赋给了局部变量 j:
int main(void)
{
int i = 10, j;
j = plus_one(i); // 这是函数调用
printf("i + 1 is %d\\n", j);
}
顺便说一下,要注意我是在使用函数之前先定义了它。如果不这样做,编译器在编译 main() 时还不知道 plus_one 存在,就会报“未知函数调用”错误。
事实上,上面的代码更合适的写法是使用函数原型(function prototypes),但我们稍后会讲这个内容。
另外要注意,main() 也是一个函数!
它返回一个 int 类型的值。
那么,void 是什么?它是一个关键字,用来表示函数不接受任何参数。
你也可以使用 void 作为返回类型,表示函数不返回任何值:
#include <stdio.h>
// 这个函数不接受参数,也不返回值:
void hello(void)
{
printf("Hello, world!\\n");
}
int main(void)
{
hello(); // 输出 "Hello, world!"
}
我之前提到过,当你把一个参数传递给函数时,会对该参数进行复制,并存储到对应的形参中。