1. 形参和实参的区别和联系
区别:形参只有在函数被调用的时候才会被分配内存,当函数结束调用后会立刻释放内存,他们所存储的值会清零,下次调用的时候,值都变成了初始值
实参可以是任何类型的数据,进行函数调用时,他们都必须有确定的值,以便把这些值传给形参
联系:实参和形参在数量上必须严格一致否则会发生“类型不匹配的错误”,如果可以类型强制转换,则可以使用不同的类型赋值
函数调用中发生的数据传递是单向的,只能把实参的值传给形参,在函数中形参的运算不影响实参的值,函数的返回值要用另外的值来接收
2. 函数的递归调用
调用一个函数的过程中有调用自己的的情况,称为递归调用,它必须有一个结束条件,当符合结束条件,函数终止
练习:
1. 判断一个数是否是素数
#include<stdio.h>
//判断是否是素数
int sushu(int a, int d)
{
if(a == 2)
{
return 1;
}
if(d == 1)
{
return 1;
}
if (a % d == 0)
{
return 0;
}
return sushu(a, d - 1);
}
int main()
{
int num;
printf("请输入一个数:\n");
scanf("%d", &num);
printf("%s\n", (sushu(num, num - 1) ? "是素数" : "不是素数"));
}
这个题我的想法是,想输入一个数,然后调用函数的时候,让 这个数和他自己-1取余,等于零则输出0,如果输入的数是2,则直接出1,不满足条件再调用自己,然后再判断自己和再次减一的情况,知道把这个数减到1,要是还不满足条件输出1,再用一个三目运算符,这个函数返回值是1则为素数,为0则不是素数
2. 输入自己手头有多钱,去买饮料,一瓶三元,喝完用瓶子可以换回一元,问可以喝多少饮料?
今天这个递归练习的时候,刚开始的时候还没有摸清递归的精髓,犯了一个错误,在递归调用中函数的函数体里的变量每次调用都会被重置数值,导致我想再递归函数中统计调用自己本身的次数,在调用结束的时候输出调用数量的时候一直都是初始值,最后我想到可以再设置一个形参,用来统计调用函数的次数,最后返回这个统计数,就可以算出我能喝到几瓶饮料了
#include<stdio.h>
//判断买多少瓶饮料
int coclor(int x, int count)
{
if(x < 3)
{
return count;
}
count++;
return coclor(x - 2, count);
}
int main()
{
int money;
int count = 0;
printf("请输入你有多少钱:\n");
scanf("%d", &money);
printf("可以喝%d瓶饮料\n", coclor(money, 0));
return 0;
}
这个题我的想法是,输入我有的钱数,递归调用函数的时候不满足条件的时候把钱数-2(- 3 + 1),每次调用用count计数,直到我的钱数小于3,跳出函数,最后输出返回值,就得到我可以喝到几瓶饮料了
总结:
今天学到了函数递归调用,感觉减少了好多代码量,但是随着我测试的数据更大,发现速度会慢很多,这比写一个函数效率低很多,所以我觉得在这个以效率优先的社会,还是尽量避免使用递归调用。不过当遇到计算很复杂的问题的时候,说不定用到递归调用问题就变得很简单,还是依情况而定。