2018.8.3
普通青蛙跳臺階問題實際上是一道斐波那契數列的題目,可以直接參考上一篇對斐波那契數列的算法分析和實現的文章——#數據結構與算法學習筆記#劍指Offer7:斐波那契數列的四種編程實現方法 + 測試用例(Java、C/C++)。
變態青蛙跳臺階問題就厲害了,思想其實本質還是斐波那契數列的思想,但是卻不需要編程循環或者遞歸模擬斐波那契的加和過程,只需要用順推的思想+數學歸納法歸納就可以確定公式 。
普通跳青蛙題目描述
一隻青蛙一次可以跳上1級臺階,也可以跳上2級。求該青蛙跳上一個n級的臺階總共有多少種跳法(先後次序不同算不同的結果)。
變態跳青蛙題目描述
一隻青蛙一次可以跳上1級臺階,也可以跳上2級……它也可以跳上n級。求該青蛙跳上一個n級的臺階總共有多少種跳法。
普通跳青蛙原理:
斐波那契數列:,其中,、。
思路:由後往前倒推,當青蛙站在第n級臺階時回顧上一步,他到達第n級臺階可以有兩種方式:1.從下一級臺階第n-1級往上跳1步,2.從下兩級臺階第n-2級往上跳2步。那青蛙到第n級臺階的方法數實際上就等於先通過前兩種方式到達上一步的方法數總和。
變態跳青蛙公式數學歸納法證明:
我們觀察有:、、、……
於是我們猜想:
通過普通跳青蛙原理的延伸,我們可以知道(十分重要):
數學歸納法證明:
① 當n = 1 時,有
② 假設當n = k時,有
③
則當n = k + 1時,
得證。
普通青蛙跳臺階編程實現:其實就是求斐波那契數列,一共有四種實現方法,可以參考上一篇文章的代碼實現,#數據結構與算法學習筆記#劍指Offer7:斐波那契數列的四種編程實現方法 + 測試用例(Java、C/C++),完全一模一樣。當然我還是貼出幾種來給大家做個參考。
普通青蛙跳臺階Java實現:
/**
*
* @author ChopinXBP
* 一隻青蛙一次可以跳上1級臺階,也可以跳上2級。求該青蛙跳上一個n級的臺階總共有多少種跳法(先後次序不同算不同的結果)。
*
*
*/
public class JumpFloor {
public static void main(String[] args) {
// TODO Auto-generated method stub
int num = Solve(5);
int num2 = Solve2(5);
System.out.println(num);
System.out.println(num2);
}
//迭代法解答,清晰明瞭,但效率極低
public static int Solve(int target) {
if (target < 3)
return target;
return Solve(target - 1) + Solve(target - 2);
}
// 最佳解答:循環順推法
public static int Solve2(int target) {
if (target == 1 || target == 2) {
return target;
}
// 第一階和第二階考慮過了,初始當前臺階爲第三階,向後迭代
// 思路:當前臺階的跳法總數=當前臺階後退一階的臺階的跳法總數+當前臺階後退二階的臺階的跳法總數
int jumpSum = 0;// 當前臺階的跳法總數
int jumpSumBackStep1 = 2;// 當前臺階後退一階的臺階的跳法總數(初始值當前臺階是第3階)
int jumpSumBackStep2 = 1;// 當前臺階後退二階的臺階的跳法總數(初始值當前臺階是第3階)
for (int i = 3; i <= target; i++) {
jumpSum = jumpSumBackStep1 + jumpSumBackStep2;
jumpSumBackStep2 = jumpSumBackStep1;// 後退一階在下一次迭代變爲後退兩階
jumpSumBackStep1 = jumpSum; // 當前臺階在下一次迭代變爲後退一階
}
return jumpSum;
}
}
普通青蛙跳臺階C++實現參考:
class Solution {
public:
int jumpFloor(int n) {
int f=1,g=2;
n--;
while(n--)
{
g+=f;
f=g-f;
}
return f;
}
};
變態青蛙跳臺階編程實現,其實就一行代碼的事情。
變態青蛙跳臺階Java實現:
/**
*
* @author ChopinXBP
* 一隻青蛙一次可以跳上1級臺階,也可以跳上2級……它也可以跳上n級。求該青蛙跳上一個n級的臺階總共有多少種跳法。
*
*
*/
public class JumpFloor2 {
public static void main(String[] args) {
// TODO Auto-generated method stub
int num = Solve(5);
System.out.println(num);
}
//可用數學歸納法證明,f(n) = 2 ^ (n - 1)
public static int Solve(int target) {
return (int)Math.pow(2, target - 1);
}
}
變態青蛙跳臺階C++實現參考:效率超高的位運算。
class Solution {
public:
int jumpFloorII(int number) {
return 1<<--number;
}
};
#Coding一小時,Copying一秒鐘。留個言點個讚唄,謝謝你#