现在时间23点34分,我想看看我几点能完成
今天总结自定义函数的使用,先从最基础的地方开始
1.形参实参
在定义函数的时候,函数大多数都有参数,在被主调函数需要传递数据给函数的参数
函数定义时用的变量叫形参
传递给函数的中形参值或变量叫实参
int main()
{
double a = 12.2;
double C = circle(2.1111); //a 是实参,实参可以是你变量,也可以是常量
printf("图的周长为:%F\n", C);
}
double circle( double r) // 这里r 是形参 形参一定是一个变量
{
return 3.1415926 * 2 * r; //返回值的类型一定是定义的函数类型,这里是double
}
注意:
1形参在未出现函数调用时,他们并不占用内存单元,只有在发生函数调用的时候形参才被分配内存,函数调用完成后,形参所占的内存被释放
2实参可以是变量,常量或者表达式
3在定义函数时,一定要指定形参的数据类型
4形参与实参的数据类型一定要可兼容
5在C语言中,实参与形参的数据传递是“值传递”,即单向传递,只由实参传递给形参,而不能由形参传递给实参。
2.函数的声明,所有自定义函数调用之前要做声明
#include<stdio.h>
//使用函数前,需要在main函数前对使用的函数进行声明
int getMax(int, int);
3.函数的返回值
1、什么是返回值
返回值是一个函数的处理结果,
2、为什么要有返回值
如果我们需要在程序中拿到函数的处理结果做进一步的处理,则需要函数必须有返回值
3、函数的返回值的应用
直接用.....
格式为:
return 值
注意:
1、return是一个函数结束的标志,函数内可以有多个return,
但只要执行一次,整个函数就会结束运行
2、return 的返回值无类型限制,即可以是任意数据类型
3、return 的返回值无个数限制,即可以用逗号分隔开多个任意类型的值
0个:返回None,ps:不写return默认会在函数的最后一行添加return None
1个:返回的值就是该值本身
多个:返回值是元组
需要强调的是,一个函数中可以有多个 return 语句,但并不是所有的 return 语句都起作用。执行到哪个 return 语句,就是哪个 return 语句起作用,该 return 语句后的其他语句就都不会执行了。
func test(x, int, y int) int {
return x + y
}
2、没有返回类型
func test(x int ,y int){
fmt.Println(x+y)
}
3、多个返回值
func test(x int, y int) (int, int, int) {
return x + y, x, y
}
4.形参的改变不能改变实参的值
比如swap函数,如果不引用指针的话在形参里修改的数值不会传到主函数里面
(1)形参出现在函数定义中,在整个函数体内都可以使用, 离开该函数则不能使用。
(2)实参出现在主调函数中,进入被调函数后,实参变量也不能使用。
(3)形参和实参的功能是作数据传送。
(4)发生函数调用时, 主调函数把实参的值传送给被调函数的形参从而实现主调函数向被调函数的数据传送。
5.swap函数实现方法,指针
#include <stdio.h>
void _swap(int *px, int * py) //因为标准库已经有swap,为了区分,你应该定义成_swap,当然也可以是别的函数名
{
int temp = *px;
*px = *py;
*py = temp;
}
int power(int x)
{
return x * x;
}
int main() // main函数本身用来测试和调用,构成一个完整的程序
{
int x, y;
printf("请输入x,y\n");
scanf("%d, %d", &x, &y);
_swap(&x, &y);
printf("交换后 x=%d, y=%d\n", x, y);
printf("power(x)=%d\n", power(y)); //此时的x是y
}
如上文所提到的,如果直接用自定义函数里面的数值做交换并不会吧值传给主函数,除了return,所以我们要用的指针,如果函数的参数是指针类型变量,在调用该函数的过程中,传给函数的是实参的地址,在函数体内部使用的也是实参的地址,即使用的就是实参本身。所以在函数体内部可以改变实参的值。
这里有个具体实现swap函数的地址:https://blog.csdn.net/apollon_krj/article/details/51445885
6.函数的递归
①递归的定义:一个函数在它的函数体内调用它自身,这种调用过程称为递归,这种函数称为递归函数。
②在递归调用中,主调函数又同时是被调函数。执行递归函数将反复调用其自身,每调用一次就进入新的一层。
③运行递归函数将无休止地调用其自身,这当然是不正确的,为了防止递归调用无终止的进行,就必须在函数内有终止递归的条件判断语句,满足某种条件后就不再作递归调用,然后逐层返回!!!这也是使用递归的难点。
递归:执行一个过程中需要再次调用该过程。
它的特点是,一个过程运算中再次用到该过程。*
他的思路是,从后往前推理。
void fun(int x)
{
if (x > 9)
{
fun(x/10);
}
printf("%d\n", x%10);
}
int main()
{
int a = 1234;
fun(a);
system("pause");
return 0;
}
(2)求n的阶乘
int factorial(int x)
{
if (x <= 1)
return 1;
else
return x* factorial(x - 1);
}
int main()
{
int x = 5;
factorial(x);
system("pause");
return 0;
}
(3)斐波那契数列
int fib(int x)
{
if (x <= 2)
return 1;
else
return fib(x - 1) + fib(x - 2);
}
int main()
{
int x = 4;
printf("%d",fib(x));
system("pause");
return 0;
}
(4)gcd函数
int Gcd(int a,int b)
{
if(b == 0) return a;
return Gcd(b,a%b);
}
6.函数的迭代
通过循环不断重复一个过程,这个过程是一个或若干个旧值通过该过程获得一个或若干个新值的过程,而得到的新值又充当下一个相同过程的旧值,直到循环得到自己期望的结果。循环执行一次过程就是一次迭代。**迭代不是循环,迭代需要用到循环。
它的特点是,一个过程结束后再次进行该过程。
它的思路是,从前往后推理。
(1)gcd函数
int Gcd(int a,int b)
{
while(b != 0)
{
int r = b;
b = a%b;
a = r;
}
return a;
}
(2)斐波那契数列
#include<stdio.h>
double Fibonacci(unsigned int n)
{
if(n==1||n==2)
return 1;
double value;
double a=1,b=1;
for(unsigned int i=3;i<=n;i++)
{
value=a+b;
a=b;
b=value;
}
return value;
}
int main()
{
int c;
printf("请输入一个数:");
scanf("%d",&c);
printf("%.0lf\n",Fibonacci(c));
return 0;
}
7.自定义函数的应用
#include<stdio.h>
int main()
{
int n = 0;
int j = 0;
int k = 0;
printf("输入你想要的乘法表数:");
scanf("%d", &n);
for (k = 1; k <= n; k++)
{
for (j = 1; j <= k; j++)
{
printf("%2d x %2d = %2d ", j, k, j*k);
}
printf("\n");
}
return 0;
}
打印一个9*9乘法表
#include<stdio.h>
int judge_leap_year(int year)
{
if ((0 == year % 4 && 0 != year % 100) || 0 == year % 400)
return 1;
else
return 0;
}
int main()
{
int year = 0;
printf("输入年份:");
scanf("%d", &year);
if (judge_leap_year(year))
printf("%d是闰年。\n", year);
else
printf("%d不是闰年。\n",year);
return 0;
}
判断是不是闰年
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
int main()
{
int number = 57;
int num = 0;
start: scanf("%d", &num);
if (num == number)
{
printf("猜对了!\n");
}
else if (num > number)
{
printf("大了,重新猜一下吧。\n");
goto start;
}
else
{
printf("小了,重新猜一下吧。\n");
goto start;
}
return 0;
}
猜数字
#include<stdio.h>
#include<math.h>
//返回-1,输入有误
//返回1,是素数
//返回因子,不是素数
int IsPrimeNumber(int number)
{
if (number <= 1)//质数是大于1的自然数
return -1;
int rooting = (int)sqrt(number);
for (int i = 2; i <= rooting; ++i)
{
if (number%i == 0)
return i;
}
return 1;
}
int main()
{
int number = 0;
int result = 0;
while (1)
{
printf("Please input a number : ");
scanf("%d", &number);
result = IsPrimeNumber(number);
if (result == -1)
printf("Input invalid.\n");
else if (result == 1)
printf("%d is primer.\n", number);
else
printf("%d isn't primer,factor is %d.\n", number,result);
}
return 0;
}
判断一个数是不是素数
文献引用:
https://blog.csdn.net/qq_43001579/article/details/81940038
https://blog.csdn.net/a1376871144/article/details/83479184
https://blog.csdn.net/pangqiandou/article/details/52772599
https://blog.csdn.net/weixin_42153410/article/details/80296299
https://blog.csdn.net/csdn_kou/article/details/80239069
https://blog.csdn.net/loterior/article/details/78322461