什么是递归?
程序调用自身的编程技巧称为递归( recursion)。
递归做为一种算法在程序设计语言中广泛应用。 一个过程或函数在其定义或说明中有直接或间接
调用自身的一种方法,它通常把一个大型复杂的问题层层转化为一个与原问题相似的规模较小的问
题来求解,递归策略只需少量的程序就可描述出解题过程所需要的多次重复计算,大大地减少了程
序的代码量。
递归的主要思考方式在于:把大事化小
递归的两个必要条件
存在限制条件,当满足这个限制条件的时候,递归便不再继续。
每次递归调用之后越来越接近这个限制条件。
今晚把这两天学的递归和做过的小题目的代码总结一下,分享给大家,欢迎评论区批评指正,互相学习!以下是源代码和运行截图
1)递归方式实现打印一个整数的每一位,例如输入:1234 输出:1 2 3 4
#define _CRT_SECURE_NO_WARNINGS 1
//递归方式实现打印一个整数的每一位
#include <stdio.h>
int fun(int num)
{
if (num > 9)
{
fun(num/10);
}
printf("%d ",num%10);
}
int main()
{
int num = 0;
printf("input:\n");
scanf("%d", &num);
fun(num);
return 0;
}
2)递归和非递归分别实现求n的阶乘(不考虑溢出的问题)
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
//递归和非递归分别实现求n的阶乘(不考虑溢出的问题)
//5!=5*4*3*2*1=120
int fun(int num)
{
int m = 1;
if (num != 0)
{
return num * fun(num-1);
}
return 1;
}
int main()
{
int num=0;
printf("input\n");
scanf("%d", &num);
int ret = fun(num);
int s = 1;
while (num >1)
{
s *= num;
num--;
}
printf("非递归求得 %d\n", s);
printf("递归求得 %d\n", ret);
return 0;
}
3)递归和非递归分别实现strlen的模拟
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
#include<string.h>
//递归和非递归分别实现strlen的模拟
int my_strlen(char *p)
{
if (*p == '\0')
{
return 0;
}
else
{
return 1 + my_strlen(p + 1);
}
}
int main()
{
char arr[] = "bit";
int num = strlen(arr);
my_strlen(arr);
printf("非递归求得字符串长度 %d\n", num);
printf("递归求得字符串长度 %d\n", my_strlen(arr));
return 0;
}
4)实现:将参数字符串中的字符反向排列,不是逆序打印。
比如: char arr[] = "abcdef";逆序之后数组的内容变成:fedcba
#define _CRT_SECURE_NO_WARNINGS 1
//实现:将参数字符串中的字符反向排列,不是逆序打印。
//要求:不能使用C函数库中的字符串操作函数。
//比如: char arr[] = "abcdef";
//逆序之后数组的内容变成:fedcba
#include<stdio.h>
void fun(char* p)
{
if (*p != '\0')
{
p++;
fun(p);
printf("%c", *(p - 1));
}
}
int main()
{
char arr[20] = { 0 };
fun(gets(arr));
return 0;
}
5)写一个递归函数,输入一个非负整数,返回组成它的数字之和
例如,调用fun(1729),则应该返回1 + 7 + 2 + 9,它的和是19
输入:1729,输出:19
#define _CRT_SECURE_NO_WARNINGS 1
//计算一个数的每位之和(递归实现)
//写一个递归函数,输入一个非负整数,返回组成它的数字之和
//例如,调用DigitSum(1729),则应该返回1 + 7 + 2 + 9,它的和是19
//输入:1729,输出:19
#include<stdio.h>
int fun(int num)
{
if (num % 10 != 0)
{
return num % 10 + fun(num / 10);
}
else
return num;
}
int main()
{
int num = 0;
scanf("%d", &num);
fun(num);
printf("各项和为 %d\n",fun(num));
return 0;
}
6)递归实现 n 的 k 次方
#define _CRT_SECURE_NO_WARNINGS 1
//递归实现 n 的 k 次方
// 2 的 3 次方 = 2*2*2
#include<stdio.h>
my_pow(int n, int k)
{
if (k != 1)
{
return n*my_pow(n , --k);
}
else
return n;
}
int main()
{
int n, k;
scanf("%d %d", &n, &k);
my_pow(n, k);
printf("%d", my_pow(n, k));
return 0;
}
7)递归实现求第n个斐波那契数
#define _CRT_SECURE_NO_WARNINGS 1
//计算斐波那契数 1 1 2 3 5 8 13 21 34 55 89 ......
//递归实现求第n个斐波那契数
//输入:10, 输出:55
#include <stdio.h>
int fib(int n)
{
if (n < 3)
return 1;
else
return fib(n-2) + fib(n - 1);
}
int main()
{
int n = 0;
printf("input:\n");
scanf("%d", &n);
fib(n);
printf("第%d个斐波那契数是%d ", n,fib(n));
return 0;
}
1. 许多问题是以递归的形式进行解释的,这只是因为它比非递归的形式更为清晰。
2. 但是这些问题的迭代实现往往比递归实现效率更高,虽然代码的可读性稍微差些。
3. 当一个问题相当复杂,难以用迭代实现时,此时递归实现的简洁性便可以补偿它所带来的运行时的开销。
以上是今晚写的C语言初阶递归小总结,欢迎大家批评指正,共同进步。