1. 能够使用递归的条件:
一般来说,能够使用递归解决问题应该满足以下3个条件:
- 需要解决的问题可以转化为一个或多个子问题来解决,而这些子问题的求解方法与原问题完全相同,只是在数量规模上不同。
- 递归调用的次数必须是有限的。
- 必须有结束递归的条件来终止递归。
2. 递归算法的设计步骤:
- 对原问题 f(sn) 进行分析,假设出合理的小问题 f(sn-1)。
- 给出 f(sn) 与 f(sn-1) 之间的关系,也就是确定递归体。
- 确定特定情况(如 f(1) 或 f(0))下的解,由此作为递归出口。
例1:采用递归算法求n!n!n!
分析:当n=0n=0n=0时,结果0!=10!=10!=1,当n≥1n\geq1n≥1时F(n)=n∗F(n−1)F(n)=n*F(n-1)F(n)=n∗F(n−1),因此递归模型为:
F(n)={1n=0n×F(n−1)n≥1F(n)=
\begin{cases}
1& \text{n=0}\\
n\times F(n-1)& \text{$n\geq1$}
\end{cases}F(n)={1n×F(n−1)n=0n≥1
根据递归模型得出以下递归算法:
int Factorial(int n)
{
if (n == 0)
return 1;
else
return (n * factorial(n - 1));
}
例2:采用递归算法求整型数组A[n]中的最小值
分析:设 f(A[],i)f(A[],i)f(A[],i) 求数组中的最小值,数组 A[]A[]A[] 中有 i+1i+1i+1 个元素,当 A[]A[]A[] 只有一个元素(i=0)时,有f(A,i)=A[0]f(A,i) = A[0]f(A,i)=A[0];假设f(A,i−1)f(A,i-1)f(A,i−1)已求出,显然有f(A,i)=Min(f(A,i−1),A[i])f(A,i) = Min(f(A,i-1), A[i])f(A,i)=Min(f(A,i−1),A[i]),其中,Min()为求两个数值中最小值的函数。因此得出以下递归模型:
f(A,i)={A[0]x=1Min(f(A,i−1),A[i])其他情况f(A,i)=
\begin{cases}
A[0]& \text{$x=1$}\\
Min(f(A,i-1), A[i])& \text{$其他情况$}
\end{cases}f(A,i)={A[0]Min(f(A,i−1),A[i])x=1其他情况
根据递归模型得出以下递归算法:
#include<stdio.h>
#include<Windows.h>
int Min(int A[], int i)
{
int min;
if (i == 0)
return A[0];
else
{
min = Min(A, i - 1);
if (min > A[i])
return A[i];
else
return min;
}
}
int main()
{
int A[] = { 53,54,123,565,41 }, min;
min = Min(A, 4);
printf("Min=%d\n", min);
system("pause");
return 0;
}
例3:递归算法求斐波那契数列(形如 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144,…的数列,这个数列从第3项开始,每一项都等于前两项之和)。
分析:当n=1或者n=2时数列值为1,从第3项开始,每一项都等于前两项之和。因此得出递归模型:
Fib(n)={1n=1,n=2Fib[n−1]+Fib[n−2]n≥3Fib(n)=
\begin{cases}
1& \text{$n=1,n=2$}\\
Fib[n-1]+Fib[n-2]& \text{$n\geq3$}
\end{cases}Fib(n)={1Fib[n−1]+Fib[n−2]n=1,n=2n≥3
根据递归模型得出以下递归算法:
int Fibonacci(int n)
{
if (n == 1 || n == 2)
return 1;
else
return (Fibonacci(n - 1) + Fibonacci(n - 2));
}

本文探讨了使用递归解决问题的条件,包括问题可转化为规模不同的子问题、有限次递归调用及存在终止条件。并详细介绍了递归算法的设计步骤,通过实例解析如何求解阶乘、数组最小值和斐波那契数列,提供了相应的递归模型和算法实现。

1950

被折叠的 条评论
为什么被折叠?



