(一)函数的定义:
-
子程序,语句块,执行特定任务,具有独立性。
- 函数分为:库函数(写好的函数)和自定义函数(造轮子)。
(二)参数:
-
形参:定义函数时的参数。形式上的参数(摆设),是实参的临时拷贝,不能改变实参。形参不开辟空间,在调用函数后悔自动销毁。
-
实参:调用函数时的参数。常量,变量,表达式,函数,必须有确定值以便传给形参。
(三)函数的组成:
- 返回类型,函数名,函数参数,函数体。
ret_type fun_name(para1, *)
{
statement;//语句项
}
(四)函数的嵌套调用和链式访问:
- 嵌套调用:可以在函数中调用其他函数,但不能在函数中定义一个新函数。
#include<stdio.h>
void test2()
{
printf("函数的嵌套调用\n");
}
int test1()
{
test2();
return 0;
}
int main()
{
test1();
return 0;
}
- 链式访问:把一个函数的返回值作为另一个函数的参数。
int main()
{
printf("%d", printf("%d", printf("%d", 43)));
//函数嵌套调用
return 0;
}
(五)函数的声明:
- 需要声明:函数叫什么,参数是什么(类型),返回类型是什么。函数在使用前要先声明(定义也算声明了)。
(六)函数的递归:
- 函数递归就是自己调用自己,有点类似循环,又有一点好像梦中梦的那种感觉。思路:大事化小。
- 函数递归的两个必要条件:
- 存在限制条件,当满足限制条件时,递归便不再继续。
- 每次递归调用之后越来越接近这个限制条件。
- 例1:把数字的位数分别打印出来(太大数字不行)
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
void print(unsigned int n)//注意返回值和形参
{
if (n > 9)//保证不会死递归
{
print(n / 10);//逼近递归跳出的条件
}
printf("%d ", n % 10);//梦中梦,梦醒了再打印
}//函数递归,大事化小,执行任务相似。
int main()
{
unsigned int num = 0;
scanf("%u", &num);//1234
//函数的递归 ------ 自己调用自己。
print(num);//print函数可以打印参数的每一位数字
return 0;
}
- 例2:打印字符串的字符的个数(不能使用局部变量)
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<string.h>
//int My_strlen(char* str)
//{
// int count = 0;
// while (*str != '\0')//不能用if,if语句是分支语句,不会循环。
// {
// count++;
// str++;//让指针往左一步指向i
// }
// return count;//注意自定义函数的返回值。
//}
int My_strlen(char* str)
{
if (*str != '\0')
{
return 1 + My_strlen(str + 1);
}//str + 1 是下一个字符的地址。在return上动手。
else
{
return 0;
}
}
int main()
{
char arr[] = { "hello" };
//模拟实现一个strlen的函数
printf("%d\n",My_strlen(arr));
return 0;
}