函数的学习(三)

1.函数的声明和定义

在C语言中,函数的声明和定义是分开的。

函数的声明是指在程序中提前告诉编译器有一个函数存在,并且指定了函数的名称、参数类型和返回值类型。函数的声明一般放在头文件中,它的作用是告诉编译器有一个函数存在,并且在其他地方可能会用到这个函数。

函数的声明的语法形式为:返回值类型 函数名(参数列表);

例如,下面是一个简单的函数声明示例:

cs 复制代码
int add(int a, int b);

函数的定义是指给出函数的具体实现。函数的定义包含函数的返回值类型、函数名、参数列表和函数体。函数的定义一般放在C源文件中,它的作用是给出函数的具体实现。

函数的定义的语法形式为:返回值类型 函数名(参数列表) {函数体}

例如,下面是一个简单的函数定义示例:

cs 复制代码
int add(int a, int b) {
    int sum = a + b;
    return sum;
}

在上面的示例中,函数的定义中包含了函数体的具体实现,在函数体中定义了一个局部变量sum,计算a和b的和,并将结果返回。

需要注意的是,函数的声明和定义必须一致,即参数类型、返回值类型和参数个数必须相同。否则,在函数调用时会发生编译错误。

如果将函数声明和定义放在同一个源文件(.h)中,位置如下:

cs 复制代码
#include<stdio.h>
//函数声明
int add(int, int);

int main()
{
	int a = 10;
	int b = 20;
	int ret = add(a, b);
	printf("ret = %d\n", ret);
	return 0;
}

//函数定义
int add(int x, int y)
{
	return x + y;
}

但是如果将加法函数看作是一个模块的话,就可以将函数声明放入头文件add.h中,将函数定义放入源文件add.c中,在主函数需要用到加法模块时,需要引入加法的头文件#include"add.h"即可。

如下所示

cs 复制代码
#include<stdio.h>

#include"add.h"

int main()
{
	int a = 10;
	int b = 20;
	int ret = add(a, b);
	printf("ret = %d\n", ret);
	return 0;
}

2.函数的递归

在C语言中,函数的递归是指函数在其定义中调用自身的过程。通过函数的递归调用,函数可以多次重复执行相同的操作,直到满足某个终止条件。

函数的递归调用一般包括以下几个要素:

1)基本情况:定义递归函数时,需要确定一个或多个基本情况,即递归调用结束的条件。一旦满足基本情况,递归将停止,不再进行调用。

2)递归调用:在函数体内部,通过调用自身来实现递归。通常在每次递归调用时,问题的规模会减小。

3)递归结束条件:递归函数必须定义一个或多个结束条件,以确保递归不会无限循环调用自身。

递归函数的实现可以通过以下步骤进行:

(1)将问题分解为一个或多个较小的问题。

(2)在函数内部调用自身,解决较小的问题。

(3)当满足基本情况时,不再调用自身,返回结果。

下面是一个简单的例子,演示如何使用递归函数按照顺序打印一个整型值(无符号)数字的每一位,如输入1234,则输出1 2 3 4,具体实现代码如下:

c 复制代码
#include<stdio.h>
void print(unsigned n)
{
	if (n > 9)
	{
		print(n / 10);
	}
	printf("%d ", n % 10);

}

int main()
{
	int  unsigned num = 0;
	scanf_s("%d", &num);
	print(num);//调用函数print()
	return 0;
}

在上面的例子中,函数printf通过递归调用自身来按顺序输出数字的每一位。当 n > 9时,递归停止。

例如输入数字1234,输出结果如下:

接下来,再看一个例子:编写代码实现计算字符串的长度

方法一:直接使用strlen()函数

方法二:调用函数,代码如下:

cs 复制代码
#include<stdio.h>
#include<string.h>
int my_strlen(char* str)//数组传参传递的是数组的首地址,所以要写成指针的形式
{
	int count = 0;

	while (*str != '\0')//字符串存储是以'\0'结尾的,但是并不算字符串的长度
	{
		count++;
		str++;
	}
	return count;
}

int main()
{
	char arr[] = "abcdef";
	int len = my_strlen(arr);
	printf("%d\n", len);
	return 0;
}

结果如下所示:

方法三:使用函数递归,代码如下:

cs 复制代码
#include<stdio.h>
#include<string.h>
int my_strlen(char* str)
{
	if (*str != '\0')
	{
		return 1 + my_strlen(str+1);
	}
	else
		return 0;
}

int main()
{
	char arr[] = "abcdef";
	int len = my_strlen(arr);
	printf("%d\n", len);
	return 0;
}

递归函数是一种强大的技术,可以用来解决多种复杂的问题。但需要注意的是,在使用递归函数时,必须确保递归能够终止,并且递归的层数不能太大,否则可能会导致栈溢出的问题。

相关推荐
掘金安东尼2 小时前
Amazon Lambda + API Gateway 实战,无服务器架构入门
算法·架构
码流之上3 小时前
【一看就会一写就废 指间算法】设计电子表格 —— 哈希表、字符串处理
javascript·算法
快手技术5 小时前
快手提出端到端生成式搜索框架 OneSearch,让搜索“一步到位”!
算法
CoovallyAIHub1 天前
中科大DSAI Lab团队多篇论文入选ICCV 2025,推动三维视觉与泛化感知技术突破
深度学习·算法·计算机视觉
NAGNIP1 天前
Serverless 架构下的大模型框架落地实践
算法·架构
moonlifesudo1 天前
半开区间和开区间的两个二分模版
算法
moonlifesudo1 天前
300:最长递增子序列
算法
CoovallyAIHub1 天前
港大&字节重磅发布DanceGRPO:突破视觉生成RLHF瓶颈,多项任务性能提升超180%!
深度学习·算法·计算机视觉
CoovallyAIHub1 天前
英伟达ViPE重磅发布!解决3D感知难题,SLAM+深度学习完美融合(附带数据集下载地址)
深度学习·算法·计算机视觉
聚客AI2 天前
🙋‍♀️Transformer训练与推理全流程:从输入处理到输出生成
人工智能·算法·llm