今日目标
- 了理解函数的定义、声明和调用。
- 掌握函数参数传递和返回值的使用方法。
- 理解递归函数的概念及其应用
- 每日练习
目录
函数
- 函数是C语言中实现代码模块化的重要工具。它可以将特定的任务封装成一个独立的单元,从而提高代码的可重用性和可维护性。
- 函数是一起执行任务的一组语句。每个C程序至少都有一个函数main(),所有最简单的程序都可以定义其他函数
- C标准库提供了程序可以调用的许多内置函数。例如,strcat()可以连接两个字符串,memcpy()可以将一个内存位置复制到另一位置,还有更多函数。函数也可以称为方法或子例程或过程等
1. 函数的定义和声明
1.1 函数定义
函数定义包括函数名、参数列表和函数体。函数体包含了要执行的代码。 C语言中函数的定义语法如下:
return_type function_name( parameter list ) {
body of the function
}
- return_type(返回类型) - 函数可以返回一个值。 return_type是值的函数返回的数据类型。某些函数执行所需的操作而不返回值。在这种情况下,return_type是关键字void。
- function_name(方法名) - 这是函数的实际名称。函数名称和参数列表共同构成函数签名。
- parameter list(参数列表) - 参数就像一个占位符。调用函数时,将一个值传递给参数。此值称为实际参数或自变量。参数列表是指函数参数的类型,顺序和数量。参数是可选的;也就是说,一个函数可能不包含任何参数。
- body of the function(函数体) - 函数体包含用于定义函数功能的语句的集合。
示例:
#include <stdio.h>
// 函数定义
int add(int a, int b) {
return a + b;
}
int main() {
int result = add(5, 3); // 函数调用
printf("Result: %d\n", result); // 输出 "Result: 8"
return 0;
}
1.2 函数声明
函数声明告诉编译器函数的名称、返回类型和参数列表,但不包含函数体。函数声明通常放在源文件的开头或头文件中。
示例:
#include <stdio.h>
// 函数声明
int add(int a, int b);
int main() {
int result = add(5, 3); // 函数调用
printf("Result: %d\n", result); // 输出 "Result: 8"
return 0;
}
// 函数定义
int add(int a, int b) {
return a + b;
}
1.3 函数调用
函数调用是通过函数名和参数列表来执行函数定义的代码。
示例:
#include <stdio.h>
// 函数定义
void greet() {
printf("Hello, World!\n");
}
int main() {
greet(); // 函数调用
return 0;
}
1.4 函数参数
函数可以有一个或多个参数,用于传递数据,在C语言传递参数分为引用传递和值传递
值传递
在函数调用时传递的是数据的副本,函数内部的修改不会影响到原来的数据。
引用传递
在函数调用时传递的是数据的地址,函数内部的修改会直接影响到原来的数据。
1.4.1 值传递
在C语言中,函数参数默认是按值传递的,即传递的是参数的副本。
示例
#include <stdio.h>
void increment(int a) {
a++;
printf("Inside function: %d\n", a); // 输出 "Inside function: 6"
}
int main() {
int num = 5;
increment(num);
printf("Outside function: %d\n", num); // 输出 "Outside function: 5"
return 0;
}
上述示例中,在main方法中将num传递给increment函数进行自增,但是increment函数执行完毕后,num的值仍然是5
为什么呢?
原因在于,当将num作为函数参数进行传递时,其实是现将复制一份num的副本,然后将副本传递给increment函数进行自增,
因此真正修改的其实是num的副本
将原程序进行如下修改
#include <stdio.h>
void increment(int a) {
printf("a address: %p \n", &a);
a++;
}
int main() {
int num = 5;
printf("num address: %p \n", &num);
increment(num);
return 0;
}
运行结果:
num address: 00FFF76C
a address: 00FFF698
从上面代码的结果可以看出函数接受的参数a
和传递给函数的参数num
的内存地址并不一样
1.4.2 引用传递
引用传递(Pass by Reference)是将实参的地址传递给函数,使函数可以直接操作实参。在C语言中,通过传递指针实现引用传递。
示例
#include <stdio.h>
// 函数定义,按引用传递参数
void modifyValue(int *a) {
*a = 10; // 修改的是实参
printf("Inside modifyValue: %d\n", *a); // 输出 "Inside modifyValue: 10"
}
int main() {
int num = 5;
modifyValue(&num); // 传递变量的地址
printf("Outside modifyValue: %d\n", num); // 输出 "Outside modifyValue: 10"
return 0;
}
由于传递的是指针,所以在modifyValue进行*a = 10;
的操作时,相当于把原本变量a的内存中的值做了修改,也就是对a本身做了修改
1.5 函数返回值
函数可以返回一个值。返回类型可以是任何基本数据类型或用户自定义类型或void
示例
#include <stdio.h>
// 函数定义
int multiply(int a, int b) {
return a * b;
}
int main() {
int result = multiply(5, 3); // 函数调用
printf("Result: %d\n", result); // 输出 "Result: 15"
return 0;
}
1.6 递归函数
递归函数是指在函数的定义中调用函数自身。递归函数必须有一个终止条件,否则会陷入无限循环
示例
#include <stdio.h>
// 递归函数定义
int factorial(int n) {
if (n == 0) {
return 1; // 终止条件
} else {
return n * factorial(n - 1); // 递归调用
}
}
int main() {
int num = 5;
printf("Factorial of %d is %d\n", num, factorial(num)); // 输出 "Factorial of 5 is 120"
return 0;
}
每日练习
练习1:打印阶梯
编写一个程序,使用函数打印指定高度的阶梯。每个阶梯由若干个
#
组成,且阶梯的高度由用户输入。
示例
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
// 函数声明
void printStairs(int height);
int main() {
int height;
printf("Enter the height of the stairs: ");
scanf("%d", &height);
printStairs(height); // 调用函数打印阶梯
return 0;
}
// 函数定义
void printStairs(int height) {
for (int i = 1; i <= height; i++) {
for (int j = 1; j <= i; j++) {
printf("#");
}
printf("\n");
}
}
运行结果
Enter the height of the stairs: 8
#
##
###
####
#####
######
#######
########
练习1:计算阶乘
编写一个程序,使用递归函数计算一个正整数的阶乘。阶乘公式为:n! = n * (n-1) * … * 1,且0! = 1。
示例
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
// 函数声明
int factorial(int n);
int main() {
int num;
printf("Enter a positive integer: ");
scanf("%d", &num);
if (num < 0) {
printf("Factorial of a negative number doesn't exist.\n");
}
else {
printf("Factorial of %d is %d\n", num, factorial(num)); // 调用函数计算阶乘
}
return 0;
}
// 递归函数定义
int factorial(int n) {
if (n == 0) {
return 1; // 终止条件
}
else {
return n * factorial(n - 1); // 递归调用
}
}
运行结果
Enter a positive integer: 10
Factorial of 10 is 3628800