完成某项特定任务的子函数
子函数功能尽量保持单一
库函数:
C/C++官方的链接:https://zh.compreference.com/w/c/neader
cplusplus.com: https://legacy.cplusplus.com/reference/clibrary/
cpp
ret_type fun_name(形式参数) //返回类型 函数名
{
//函数体
}
子函数返回类型和形式参数可以是void
void nothing ( void ){
}
返回类型void表示函数执行完毕后不返回任何值
形参void表示函数没有参数
c
#include <stdio.h>
// 子函数:实现两个整数的加法
int add(int a, int b) { //括号里是形参(形式参数)
return a + b;
}
int main() {
int num1 = 5;
int num2 = 3;
int result = add(num1, num2); // 调用子函数,括号里是实参(实际参数)
printf("The sum of %d and %d is %d\n", num1, num2, result);
return 0;
}
retun 语句
return后边可以是一个数值,也可以是一个表达式,如果是表达式则先执行表达式,再返回表达式的结果
retun后边也可以什么都没有,直披写 return;这种写法适合函数返回类型是void的情况
return返口的值和函数返回类型不一致,系统会自动将返回的值转换为函数的返回类型
return语句执行后函数就彻底返问,后边的代码不再执行
如果函数中存在if等分支的语句,则要保证每种情况下都有return返回,否则会出现编译错误
数组传参
实参和形参名可以一致也可以不一致
数组实参是数组名,形参是数组的形式
传参的时候,形参和实参的数组是同一个数组
二维数组传参
如果形参是二维数组,行可省略,列不可省
cpp
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
//打印二维数组
void print(int arr[][6],int a,int b) {
for (int i = 0; i < a; i++) {
for (int j = 0; j < b; j++) {
printf("%d ", arr[i][j]);
}
printf("\n");
}
}
int main() {
int arr[][6] = { 1,2,3,4,5,6, 1,2,3,4,5,6, 1,2,3,4,5,6 };
print(arr,3,6);
return 0;
}
嵌套调用
计算某年某月有多少天
cpp
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
int leap_month(int year) {
if ((year % 100 != 0 && year % 4 == 0) || year % 400 == 0)
return 1;
else
return 0;
}
int get_year_month(int year, int month) { //计算某年某月有多少天
//一共12个月,每个月的天数,第一个数字为0,方便计算闰年二月
int days[] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 };
int day = days[month]; //某个月的天
if (leap_month(year) && month == 2) {
day++;
}
return day;
}
int main() {
int year = 0;
int month = 0;
scanf("%d %d", &year, &month);
int day = get_year_month(year, month); //计算某年某月有多少天
printf("%d\n", day);
return 0;
}
可以把leap_month函数换成bool类型
cpp
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<stdbool.h>
bool leap_month(int year) {
if ((year % 100 != 0 && year % 4 == 0) || year % 400 == 0)
return true;
else
return false;
}
int get_year_month(int year, int month) { //计算某年某月有多少天
//一共12个月,每个月的天数,第一个数字为0,方便计算闰年二月
int days[] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 };
int day = days[month]; //某个月的天
if (leap_month(year) && month == 2) {
day++;
}
return day;
}
int main() {
int year = 0;
int month = 0;
scanf("%d %d", &year, &month);
int day = get_year_month(year, month); //计算某年某月有多少天
printf("%d\n", day);
return 0;
}
链式访问
一个函数中参数使用了其他函数
cpp
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<string.h>
int main() {
//int len = strlen("abcdef");
//printf("%d\n",len);
printf("%d\n", strlen("abcdef")); //一个函数中参数使用了其他函数
return 0;
}
cpp
printf("%d", printf("%d", printf("%d", 43)));
结果:4321
2和1是因为printf输出占用的字符数
过程:
printf("%d", printf("%d", 43));
printf("%d", 2);
1
cpp
printf("%d ", printf("%d ", printf("%d ", 43)));
结果:43 3 2
空格也占一个字符
函数的声明和定义
.lib文件时一个静态库
函数的声明、类型的声明 一般放在头文件里里
函数的实现放在源文件里
要注意作用域,extern用来声明外部符号,text1里int a = 100;则在text2里要写extern int a;
如果就是子函数写在main函数后面,子函数要先声明再使用,声明可以不写参数
如果就是子函数写在main函数前面,也可以,因为函数的定义是特殊的声明
cpp
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<stdbool.h>
bool leap_month(int);
int get_year_month(int, int);
int main() {
int year = 0;
int month = 0;
scanf("%d %d", &year, &month);
int day = get_year_month(year, month); //计算某年某月有多少天
printf("%d\n", day);
return 0;
}
bool leap_month(int year) {
if ((year % 100 != 0 && year % 4 == 0) || year % 400 == 0)
return true;
else
return false;
}
int get_year_month(int year, int month) { //计算某年某月有多少天
//一共12个月,每个月的天数,第一个数字为 0,方便计算闰年二月
int days[] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 };
int day = days[month]; //某个月的天
if (leap_month(year) && month == 2) {
day++;
}
return day;
}
static静态变量
在局部变量前加上static就改变了局部变量的生命周期,就跟全局变量的生命周期一样,但作用域不变还是局部。
什么时候用?
在一个变量出了函数后,我们还想保留它的值,等下次进入函数继续使用,比如static int a = 1;
|-----|----------------------------------|
| 栈区 | 局部变量、函数参数 |
| 堆区 | 动态内存管理malloc、calloc、realloc、free |
| 静态区 | 全局变量、静态变量 |
变量在使用前也得声明
extern init a;