2023-04-23 学习记录--C/C++-函数
合抱之木,生于毫末;九层之台,起于累土;千里之行,始于足下。💪🏻
【一】、调用有参函数 ⭐️
有参函数:调用函数时,需要
传对应参数
。
一、实现步骤 🌸
实现步骤:💐
- (一)、申明函数
- (二)、定义/封装函数
- (三)、调用函数
(一)、申明函数 🍭
1、一般形式 🎠
函数结果类型
函数名
(参数类型1
参数名1
,参数类型2
参数名2
, … ,参数类型n
参数名n
);
2、example1:🎈
float
max
(float
x
,float
y
); // 申明函数max
:有两个形参x
、y
(均为单精度浮点型),函数结果也是单精度浮点型
3、example2:🎈
void
max
(float
x
,float
y
); // 申明函数max
:有两个形参x
、y
(均为单精度浮点型),函数无返回值
(函数结果类型为void
)
(二)、定义/封装有参函数 🍭
1、一般形式 🎠
函数结果类型 函数名(参数类型1 参数名1, 参数类型2 参数名2, ..., 参数类型n 参数名n)
{声明部分 ------ 声明各种变量、常量、函数等语句部分 ------ 各表达式(返回值) ------ 可有可无,应需求而定【无返回值时,函数结果类型为void】
}
2、注意事项 👁
- 定义/封装函数 时,必须指定
函数结果类型
(无返回值
时,类型是void
)和各形参类型
;
(三)、调用函数 🍭
1、一般形式 🎠
函数名
(参数值1
,参数值2
, … ,参数值n
);
2、注意事项 👁
- 调用函数 时,
传入的实参
需与定义/封装函数时的形参
在个数
、类型
、顺序
上保持一致; - 调用函数
传数组
时只用写数组名
就相当于把数组传过去了。
二、举例 🌸
example1:🎈
需求:有两个小组,分别有5名学生和10名学生。请编程输入这些学生的成绩,并调用一个aver函数求这两个小组的平均分。
/* 需求:有两个小组,分别有5名学生和10名学生。请编程输入这些学生的成绩,并调用一个aver函数求这两个小组的平均分。*/#include <stdio.h>
int main()
{/ 使用变量/常量/函数前必须先声明 */float aver(float a[], int n); // 声明函数aver:有两个形参a[](数组,数组元素为单精度浮点型)、n(数组个数,整数型),函数结果是单精度浮点型float arr1[5], arr2[10]; // 声明两个一维数组arr1、arr2int i;/ 引导用户输入学生成绩 */printf("请输入第1组的学生成绩:\\n"); // 提示信息for (i = 0; i < 5; i++)scanf("%f", &arr1[i]); // for语句依次输入第1组学生的成绩printf("请输入第2组的学生成绩:\\n"); // 提示信息for (i = 0; i < 10; i++)scanf("%f", &arr2[i]); // for语句依次输入第2组学生的成绩/ 输出结果 —— 调用函数获取到平均分 */printf("第1组平均分是%f\\n", aver(arr1, 5)); // 传数组时只用写数组名就相当于把数组传过去了printf("第2组平均分是%f\\n", aver(arr2, 10)); // 传数组时只用写数组名就相当于把数组传过去了/ 程序正常运行结束 */return 0;
}/* 定义/封装函数:求数组元素的平均值* @param {a[]} a[] 数组* @param {int} n 数组个数* @return 平均值* */
float aver(float a[], int n)
{/ 声明部分 */float sum = a[0], average;int i;/ 语句部分 */for (i = 1; i < n; i++) // i初始值为1:因为sum的初始值是a[0](数组里的第一个元素),所以第一个元素没必要再遍历一次了sum += a[i];average = sum / n; // 获取到平均值/ 返回值 */return (average);
}
example2:🎈
需求:请编程输入10个整数,并将这10个数由小到大排序。
/* 需求:请编程输入10个整数,并将这10个数由小到大排序。*/#include <stdio.h>
int main()
{/ 使用变量/常量/函数前必须先声明 */void sort(int a[], int n); // 声明函数sort:有两个形参a[](数组,数组元素为单精度浮点型)、n(数组个数,整数型),函数结果是单精度浮点型int a[10], i;/ 引导用户输入10个整数 */printf("请输入10个整数:\\n"); // 提示信息for (i = 0; i < 10; i++)scanf("%d", &a[i]); // 用户输入/ 调用函数 —— 升序 */sort(a, 10); // 传数组时只用写数组名就相当于把数组传过去了/ 输出结果 */printf("排序后的整数依次是:\\n"); // 提示信息for (i = 0; i < 10; i++)printf("%d\\t", a[i]);printf("\\n"); // 最后一个输出语句,一定要记得加上换行符(\\n)/ 程序正常运行结束 */return 0;
}/* 定义/封装函数:选择法实现升序* @param {a[]} a[] 数组* @param {int} n 数组个数* @return 无返回值* */
void sort(int a[], int n)
{/ 声明部分 */int i, j, t;/ 语句部分 */for (i = 0; i < n - 1; i++) // i初始值为1:因为sum的初始值是a[0](数组里的第一个元素),所以第一个元素没必要再遍历一次了for (j = i + 1; j < n; j++)if (a[i] > a[j]){t = a[i];a[i] = a[j];a[j] = t;}
}
【二】、调用无参函数 ⭐️
无参函数:调用函数时,
不需要传对应参数
。
一、实现步骤 🌸
实现步骤:💐
- (一)、申明函数
- (二)、定义/封装函数
- (三)、调用函数
(一)、申明函数 🍭
1、一般形式 🎠
函数结果类型
函数名
();
2、example1:🎈
float
sort
(); // 申明函数sort
:不含参数,函数结果是单精度浮点型
3、example2:🎈
void
sort
(); // 申明函数sort
:不含参数,函数无返回值
(函数结果类型为void
)
(二)、定义/封装无参函数 🍭
1、一般形式 🎠
函数结果类型 函数名()
{声明部分 ------ 声明各种变量、常量、函数等语句部分 ------ 各表达式(返回值) ------ 可有可无,应需求而定【无返回值时,函数结果类型为void】
}
2、注意事项 👁
- 定义/封装函数 时,必须指定
函数结果类型
(无返回值
时,类型是void
);
(三)、调用函数 🍭
1、一般形式 🎠
函数名
();
2、注意事项 👁
- 调用函数
传数组
时只用写数组名
就相当于把数组传过去了。
二、举例 🌸
下面声明 一个无返回值的无参函数 和 一个有返回值(返回值类型为字符型)的无参函数为例:
#include <stdio.h>int main()
{/ 使用变量/常量/函数前必须先声明 */void output(); // 声明一个无返回值的无参函数char get(); // 声明一个有返回值(返回值类型为字符型)的无参函数/ 调用函数 */output();printf("得到一个字符:%c\\n", get()); // 记得加换行符/ 程序正常运行结束 */return 0;
}/* 定义/封装函数*/
// 输出一句话
void output()
{printf("冲冲冲哇~\\n"); // 记得加换行符
}
// 返回一个字符
char get()
{return 'a';
}
【三】、函数的嵌套 ⭐️
(一)、含义 🌸
函数的嵌套:
函数里面再嵌套函数
。
(二)、举例 🌸
需求:请编程输入4个整数,并找出其中最大的数。
/* 需求:请编程输入4个整数,并找出其中最大的数。*/#include <stdio.h>
int main()
{/ 使用变量/常量/函数前必须先声明 */int max4(int a, int b, int c, int d); // 声明函数max4:有4个形参a、b、c、d,均为整数型,函数结果也是整数型int a, b, c, d, max;/ 引导用户输入10个整数 */printf("请输入4个整数(以空格隔开):\\n"); // 提示信息scanf("%d %d %d %d", &a, &b, &c, &d); // 用户输入/ 调用函数 —— 获取4个整数里的最大值 */max = max4(a, b, c, d);/ 输出结果 */printf("最大数为%d\\n", max);/ 程序正常运行结束 */return 0;
}/* 定义/封装函数:获取4个整数里的最大值* @return 4个整数里的最大值* */
int max4(int a, int b, int c, int d)
{/ 声明部分 */int max2(int a, int b); // 函数使用前必须声明/ 返回值 */return (max2(max2(max2(a, b), c), d)); // 函数嵌套
}/* 定义/封装函数:获取2个整数里的最大值* @return 2个整数里的最大值* */
int max2(int a, int b)
{/ 返回值 */return (a > b ? a : b);
}
【四】、函数的递归 ⭐️
(一)、含义 🌸
函数的递归:
函数里面调用函数自己
。
(二)、举例 🌸
example1:🎈
#include <stdio.h>int main()
{/ 使用变量/常量/函数前必须先声明 */int ageFun(int n); // 声明函数/ 输出结果 */printf("第5个学生的年龄为%d\\n", ageFun(5));/ 程序正常运行结束 */return 0;
}/* 定义/封装函数:计算年龄* @param {int} n 整数* @return 年龄* */
int ageFun(int n)
{int age; // 年龄age = n == 1 ? 10 : ageFun(n - 1) + 2;return age;
}
example2:🎈【重要】
需求 🌈:
用递归方法求n!(n的阶乘)
。
分析 📚:
- 1、
负数没有阶乘
;- 2、
0和1的阶乘为1
;
- 1! = 1 = 0! * 1;
0! = 1; 【1! = 1 = 0! * 1 👉🏻 0! = 1】- 3、
大于等于2的阶乘:
2! = 1 * 2= 1! * 2;(2)
3! = 1 * 2 * 3 = 2! * 3;(6)
4! = 1 * 2 * 3 * 4 = 3! * 4;(24)
。。。
n! = 1 * 2 * 3 * 4 * … * n-1 * n = (n-1)! * n;
规律为:n! = (n-1)! * n;
/* 需求:用递归方法求n!(n的阶乘)。*/#include <stdio.h>
#include <stdlib.h>
#include <limits.h>int main()
{/ 使用变量/常量/函数前必须先声明 */unsigned long long factorial(int n); // 声明函数int n;/ 引导用户输入 */printf("请输入一个正整数n:"); // 提示信息scanf("%d", &n); // 用户输入n < 0 ? printf("输入错误!\\n") : printf("%d! = %llu\\n", n, factorial(n)); // 负数没有阶乘return 0;
}/* 定义/封装函数:获取n的阶乘* @param {int} n 整数* @return n的阶乘* */
unsigned long long factorial(int n)
{if (n == 0 || n == 1){ // 阶乘0和1都为1return 1;}else{unsigned long long res = factorial(n - 1); // 递归求解n-1的阶乘// 防止溢出// ULLONG_MAX常量是在limits标头中定义的宏常量,用于获取无符号long long int对象的最大值,它返回一个无符号long long int对象可以存储的最大值,即18446744073709551615 (在32位编译器)。if (res > ULLONG_MAX / n){printf("Error: 哦豁!我只能求%d以下滴阶乘哦~\\n", n);/* EXIT_FAILURE作为exit()的参数来使用,表示没有成功地执行一个程序;* EXIT_SUCCESS作为exit()的参数来使用,表示成功地执行一个程序。* 二者对应需引入的头文件是:#include <stdlib.h>*/exit(EXIT_FAILURE);}return res * n; // 返回n的阶乘}
}