一、斐波那契数列
斐波那契数列(Fibonacci sequence),又称黄金分割数列、因数学家列昂纳多·斐波那契(Leonardoda Fibonacci)以兔子繁殖为例子而引入,故又称为“兔子数列”,指的是这样一个数列:1、1、2、3、5、8、13、21、34、……在数学上,斐波纳契数列以如下被以递推的方法定义:F(1)=1,F(2)=1, F(n)=F(n-1)+F(n-2)(n>=3,n∈N*)。
斐波那契数列的解法有递归(写法简单,复杂度高)和循环(写法较复杂,但复杂度低)两种。
斐波那契数列的变种问题:走楼梯问题、矩形全覆盖问题。
二、跳台阶问题
一只青蛙一次可以跳上1级台阶,也可以跳上2级。求该青蛙跳上一个n级的台阶总共有多少种跳法(先后次序不同算不同的结果)。
分析:
一般情况:青蛙的第一步有两种跳法,跳一级或者跳两级。如果跳一级那么问题转化为:f(n)=f(n-1)。如果跳两级那么问题转化为:f(n)=f(n-2)。
所以:f(n)=f(n-1)+f(n-2),即斐波那契数列。
特殊情况:如果有一个台阶,那么只有一种跳法。记为:f(1)=1。如果有两个台阶,那么有两种跳法,f(2)=2。
所以问题为:f(1)=1,f(2)=2,f(n)=f(n-1)+f(n-2)的斐波那契数列问题。
class Solution {
public:
int jumpFloor(int number) {
if(number<=2)
{
return number;
}
int ppre=1,pre=2,k;
k=ppre+pre;
for(int i=3;i<number;++i)
{
ppre=pre;
pre=k;
k=ppre+pre;
}
return k;
}
};
进阶:一只青蛙一次可以跳上1级台阶,也可以跳上2级……它也可以跳上n级。求该青蛙跳上一个n级的台阶总共有多少种跳法。
分析:
一般情况:青蛙在第一跳的时候就有n中选择(当青蛙第一次跳为n级时,之后的跳法为0,即f(n-n)=f(0)=0)。所以:
f(n)=f(n-1)+f(n-2)+......f(2)+f(1)
简化规律:f(n-1)=f(n-2)+f(n-3)+......+f(2)+f(1)
所以:f(n)=2*f(n-1)
特殊情况:n=0,f(0)=0;n=1,f(n)=1;n=2,f(n)=2。
class Solution {
public:
int jumpFloorII(int number) {
if(number<3)
{
return number;
}
return 2*jumpFloorII(number-1);
}
};
三、矩形全覆盖问题
我们可以用2*1的小矩形横着或者竖着去覆盖更大的矩形。请问用n个2*1的小矩形无重叠地覆盖一个2*n的大矩形,总共有多少种方法?
思路:
一般情况:小矩形在大矩形中横着放,会占大矩形中两个格子,即转化为:f(n)=f(n-2);小矩形在大矩形中竖着放,会占大矩形中一个格子,即转化为:f(n)=f(n-1)。所以f(n)=f(n-1)+f(n-2)
特殊情况:n=1,f(1)=1;n=2,f(2)=2。
代码和上面的代码相同,这里就不赘述了。