C语言函数详解

1.1        函数的原型和调用
1 ,定义一个函数
有返回值的情况:
double circle( double r) // 这里r 是形参 形参一定是一个变量
{
return 3.1415926 * 2 * r; //返回值的类型一定是定义的函数类型,这里是double
}
返回值的情况:
void sayhello(char s[])
{
printf("hello,%s!!!\n",s);
}

2 在使用函数前必须定义或者声明函数
#include <stdio.h>
 double circle(double r);
void sayhello(char s[]);//当函数在main函数前定义的时候,在使用函数前,必须先声明

1.2    函数的形参与实参
在定义函数的时候,函数大多数都有参数,在被主调函数需要传递数据给函数的参数
函数定义时用的变量叫形参
传递给函数的中形参值或变量叫实参
int main()
{
	double a = 12.2;
	double C = circle(2.1111); //a 是实参,实参可以是你变量,也可以是常量
	printf("图的周长为:%F\n", C);
	sayhello("inx");
}
double circle( double r)      // 这里r 是形参 形参一定是一个变量
{
	return 3.1415926 * 2 * r; //返回值的类型一定是定义的函数类型,这里是double
}

注意:
1 形参在未出现函数调用时,他们并不占用内存单元,只有在发生函数调用的时候形参才被分配内存,函数调用完成后,形参所占的内存被释放
2 实参可以是变量,常量或者表达式
3 在定义函数时,一定要指定形参的数据类型
4 形参与实参的数据类型一定要可兼容
5 C 语言中,实参与形参的数据传递是“值传递”,即单向传递,只由实参传递给形参,而不能由形参传递给实参。
演示值传递:
#include <stdio.h>
void value_pass();

int main()
{
	double a = 12.2;
	value_pass(a);
	printf("a=%F", a); //当a传递给函数形参a的时候,只是把值赋给a,a=12.200000 
	return 0;
}
void value_pass(double a)
{
	a = a + 2;
	printf("a=%F", a);//输出结果 a + 2;
}

输出结果:
a=14.200000
a=12.200000

注:如果函数的参数是个数组,或者字符串的时候,那么是可以通过形参修改实参的值的()

1.3        函数的返回类型与返回值
1 函数的返回值通过函数中的 return 获得,如果函数的返回值为 void 可以不需要 return 语句。
2 函数 return 语句中的返回值数据类型应该与函数定义时相同。
3 如果函数中没有 return 语句,那么函数将返回一个不确定的值。

1.4        main 函数与 exit 函数与函数的 return 语句
代码:
exit(0);//退出程序
return 0;//退出函数
 
1.5        多个源代码文件程序的编译
1.5.1           头文件的使用
如果把 main 函数放在第一个文件中,而把自定义函数放在第二个文件中,那么就需要在第一个文件中声明函数原型。
如果把函数原型包含在一个头文件里,那么就不必每次使用函数的时候都声明其原型了。把函数声明放入头文件是很好的习惯。
1.5.2           #include #define 的意义
#include 就是简单的文件内容替换
#define 就是简单的文本替换而已
1.5.3           #ifndef #endif
#ifndef 的意思就是条件预编译 , 如果 #ifndef 后面的条件成立,那么就预编译从 #ifndef 开始到 #endif 之间的代码,否则不会去预编译这段代码
 
1.6        函数的递归
函数可以调用自己,这就叫函数的递归:
先序递归演示:
代码
#include <stdio.h>
void test(int n)
{
	printf("n=%d\n", n);
	n--;
	if ( n > 0)
	{
		test(n);
	}
}
int main()
{
	int i = 10;
	test(i);
}

打印结果:
n=10
n=9
n=8
n=7
n=6
n=5
n=4
n=3
n=2
n=1

后序递归(主体在递归后面):
代码
#include <stdio.h>

void test(int n)
{
	n--;
	if ( n > 0)
	{
		test(n);
	}
	printf("n=%d\n", n);
}
int main()
{
	int i = 10;
	test(i);
}


显示结果:
n=0
n=1
n=2
n=3
n=4
n=5
n=6
n=7
n=8
n=9
 
1.6.1           递归的过程分析


n 个人排成一队,问第 n 个人多少岁,他回答比前面一个人大 2 岁,再问前面一个人多少岁,他回答比前面一个人大 2 岁,一直问到最后问第一个人,他回答 10
代码:
#include <stdio.h>
int age(n)
{
	if (n == 1)
	{
		return 10;
	}
	else
	{
		return age(n - 1) + 2;
	}
}

int main()
{
	int n = 10;
	printf("第N个人%d岁\n",age(10));
}

 打印结果:
第N个人28岁

10 进制数转化为二进制数的例子
234 在十进制下为 2 * 10 2 次方 + 3 * 10 1 次方 + 4*10 0 次方。
奇数的二进制最后一位一定是 1 ,偶数的二进制最后一位一定是 0
可以通过 number % 2 得到二进制形式的最后一位,如果要将一个完整的整数转化为二进制就需要用到递归函数。
在递归调用之前,计算 number % 2 的值,然后在递归调用语句之后进行输出,这样计算出的第一个数值反而在最后一个输出。
为了得出下一个数,需要把原数除以 2 ,这种计算相当于十进制下把小数点左移一位,如果此时得出的数是偶数,,则下一个二进制的数值是 0 ,如果得出的是奇数,那么下一个二进制数为 1
直到被 2 除的结果小于 2 ,就停止递归。
代码:
int bin(int n) //将十进制n 转化为二进制数
{
int a = n % 2;
int b = n / 2;
if (b > 0)
{
bin(b);
}
printf("%d",a);
}
int main()
{
int n = 100;
bin(n);
//printf("第N个人%d岁\n",age(10));
打印结果:
1100100
 
斐波那契数列例子
斐波那契数列指的是这样一个数列 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, ...
0 项是 0 ,第 1 项是第一个 1
这个数列从第 2 项开始,每一项都等于前两项之和。
代码:
int fib(n)
{
	if (n == 1) 
		return 0;
	if (n == 2)
	{
		return 1;
	}
	if (n >= 3)
	{
		return fib(n - 2) + fib(n - 1);
	}
}
int main()
{
	int n = 10;
	printf("fibs前10项为:");
	for (int i = 1; i <= n;i++)
	{
		printf("%d ",fib(i));
	}
	//printf("第N个人%d岁\n",age(10));
} 

打印结果:
fibs前10项为:0 1 1 2 3 5 8 13 21 34
1.6.2           递归的优点
递归给某些编程问题提供了最简单的方法
1.6.3           递归的缺点
一个有缺陷的递归会很快耗尽计算机的资源,递归的程序难以理解和维护。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

crystalnsd

万水千山总是情,支持一下行不行

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值