版权声明:本文为博主原创文章,评论区告知一声,大家随意转载! https://blog.csdn.net/MessageBox_/article/details/84671735
题目如下:
一只青蛙一次可以跳上1级台阶,也可以跳上2级……它也可以跳上n级。求该青蛙跳上一个n级的台阶总共有多少种跳法。
解题思路:
其实有两种解题思路,个人更倾向于第二种方法,应为个人觉得它更符合计算机解决问题的思路。
在这道题目之前,其实还有一个简单的青蛙跳台阶,就是青蛙可以跳一次和跳两次,这个其实很简单也没啥好说的,使用递归就可以得到我们想要的结果。
我们看看这道题,我一开始的想法也是使用递归,最后发现其实还是那么回事。。。
思路一:
假设 青蛙跳到n级的方法是 F(n)
那么F(n)是怎么来的呢?我们从后往前思考
1.青蛙跳到第n-1级,最后跳1步 ,而跳到n-1级的跳法是F(n-1) A1 = F(n-1)
2.青蛙跳到第n-2级,最后跳2步 ,而跳到n-2级的跳法是F(n-2) A2 = F(n-2)
.....
n-1.青蛙跳到第1级,最后跳n-1步 ,而跳到1级的跳法是F(1) An-1 = F(1)
n. 青蛙直接跳n级,An = 1
那么我么可以得到如下结果:
a. F(n) = A1 + A2 + …+ An-1 + An = F(n-1) + F(n-2) + … + F(1) + 1
b. F(n-1) = F(n-2) + … + F(1) + 1
c. F(n) = F(n-1) + F(n-1) = 2F(n-1)
所以结果就很简单了
function jumpFloorII(number)
{
if( number === 1){
return 1;
}else{
return 2 * jumpFloorII(number - 1);
}
}
所以这道题究竟是算法呢还是数学呢?。。。。
思路二:
这个方法是我查看其他解法时发现的,本质和思路一差不多,不同的地方在于它并没有上文中的推理步骤b和c,仅仅是依靠公式a就得到的最终的结果,下面让我们一起看看代码
function jumpFloorII(number)
{
if(number === 1){
return 1;
}else if( number > 1){
//创建一个空数组,用来保存对应每一个小于number的n的跳法结果
let arr = new Array(number + 1).fill(0);
arr[0] = 0;
arr[1] = 1;
for(let i = 2; i <= number; i++ ){
// An = An-1 + An-2 + ... + A1 + 1
for( let j = 1 ; j < i ; j++ ){
arr[i] += arr[j];
}
arr[i] += 1;
}
return arr[number];
}else{
return -1;
}
}
巧妙的使用数组,将每一次的An-1计算结果保存起来,而后面的An的计算结果是依赖前面的A1…An-1的。