递推算法的基本思想是把一个复杂的、庞大的计算过程转化为简单过程的多次重复,其首要问题是得到相邻的数据项之间的关系,即递推关系。以猴子爬山为例。
1.问题的提出
一个顽猴在一座有30级太假的小山上爬山活跃,猴子上一步可跳1级或者3级,试求上山的30级台阶有多少种不同的爬法
2.简单递推设计
这一问题实际上是一个整数有序可重复拆分的问题。试应用数组递推求解,设爬k级台阶的不同爬法为f(k)种。
- 探求f(k)的递推关系
上山最后一步到达第30级台阶,完成上山,共有f(30)种不同的爬法,到第30级之前位于哪一级呢?无非就是位于第29级(上跳1级即可到),有f(29)种;或者位于第27级(上跳3级即可到),有f(27)种;于是f(30)=f(29)+f(27)
依次类推,有以下递推关系:
f(k) = f(k-1)+f(k-3) (k>3)
- 确定初始条件
f(1) = 1
f(2) = 1
f(3) = 2
3.递推描述
n = int(input()) #总共需要到达的台阶数
result = []
if(n==1):
print(1)
elif(n==2):
print(1)
elif(n=3):
print(2)
else:
result.append(0)
result.append(1)
result.append(1)
result.append(2)
for i in range(4,n+1):
result.append(result[i-1]+result[i-3])
print(result.pop())
以上是一般爬楼梯的形式,也有很多以上面这种改编的题目,比如今天刷到的快手的校招题--魔法深渊: 已知深渊有N层台阶构成(1 <= N <= 1000),并且每次月神仅可往上爬2的整数次幂个台阶(1、2、4、....),请你编程告诉月神,月神有多少种方法爬出深渊。链接:https://www.nowcoder.com/practice/55e34723b1d34c42af83b39de2395408tpId=98&tqId=32842&tPage=1&rp=1&ru=/ta/2019test&qru=/ta/2019test/question-ranking
我们建立递推关系:
,其中
。感觉和上面基础版的题目是一个套路,以下是Java实现的代码:
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner sc = new Scanner(System.in);
int M = sc.nextInt();
int[] d = new int[M];
for(int i=0;i<M;i++)
d[i] = sc.nextInt();
for(int i=0;i<M;i++) {
System.out.println(put(d[i]));
}
}
public static long put(int n) {
if(n==1) {
return 1%((int) Math.pow(10, 9)+3);
} else if(n==2) {
return 2%((int) Math.pow(10, 9)+3);
} else if(n==3) {
return 3%((int) Math.pow(10, 9)+3);
} //上面这些都是初始条件
else {
long[] dp = new long[n+1];
dp[0] = 1;
dp[1] = 1;
dp[2] = 2;
dp[3] = 3;
for(int i=4;i<=n;i++) { //从这里开始建立递推关系
int k=0;
int j=(int) (i-Math.pow(2, k));
while(j>=0) {
dp[i]+=(dp[j]%(Math.pow(10, 9)+3));
k+=1;
j=(int) (i-Math.pow(2, k));
}
}
return (long) (dp[n]%(Math.pow(10, 9)+3));
}
}
}
本文介绍了递推算法的概念,通过猴子爬山问题和快手校招题——魔法深渊为例,阐述了如何利用递推关系解决问题。猴子爬山问题中,猴子上山的30级台阶有多种不同的爬法,通过递推公式f(k) = f(k-1)+f(k-3) (k>3)来解决。魔法深渊问题要求月神以2的整数次幂阶数爬出深渊,同样可以建立递推关系进行求解,并给出了Java实现代码。
6757





