题目3:一段楼梯共n级台阶,规定每一步只能跨一级或两级或三级。要等上第n级台阶共有几种走法?
斐波那契数列问题:递归或动态规划均可解此类问题。跳台阶是典型应用之一。
思路:我们先从最后开始考虑,因为规定每一步只能跨一级或两级或三级,那么:
从第9级爬上去的可能性有1种; #跨一级:1
从第8级爬上去的可能性有2种; #连续跨一级或者跨两级:11,2
从第7级爬上去的可能性有4种; #穷举:111,12,21,3
然后用递归的思想,把楼梯共10级台阶替换成楼梯共9级台阶/楼梯共8级台阶/楼梯共7级台阶…
我们设爬n级台阶的解法总数为f(n),因为规定每一步只能跨一级或两级或三级,则f(n)=f(n-1)+f(n-2)+f(n-3)。
用穷举法求初始条件:
n=1时,f(n)=1;
n=2时,f(n)=2;
n=3时,f(n)=4;
n=4时,f(n-1)+f(n-2)+f(n-3)=f(n)=f(4)=f(3)+f(2)+f(1);
…
解法1
#只用有放回抽样算法无法解决抽样顺序问题
def climb_stair(n):
z=[]
nl=[]
for x in range(n+1):
nl.append(x)
nl_3 = nl+nl+nl
for i in itertools.permutations(nl_3,3):
if i[0]+2*i[1]+3*i[2]==n:
z.append(i)
z=list(set(z))
z_len=len(z)
return z,z_len
if __name__=='__main__':
n=3
z,z_len=climb_stair(n)
print(z)
print(z_len)
解法2
动态规划
def jumpFloor(a):
n = int(a) #很重要,输入的台阶数目取整
if n == 1:
return 1 #Python的return后可以加“;”或者省略
elif n == 2:
return 2
elif n == 3:
return 4
else:
z = jumpFloor(n-1)+jumpFloor(n-2)+jumpFloor(n-3)
return (z) #可以把变量替代省略,返回值里直接写成公式
n = input('Please give a number:')
print('The number of solutions is:', jumpFloor(n))
解法3
class Solution:
def __init__(self,n):
self.n=n
def climbStairs(self):
"""
:type n: int
:rtype: int
"""
res = []
res.append(1)
res.append(1)
res.append(2)
res.append(4)
if self.n<=1:
return 1
elif self.n==2:
return 2
elif self.n==3:
return 4
else:
for i in range(4,self.n+1):
res.append(res[-1]+res[-2]+res[-3])
return res[-1]
if __name__=='__main__':
n = int(input('Please give a number:'))
sol=Solution(n)
print(sol.climbStairs())
解法4
def climbStairs(n):
"""
:type n: int
:rtype: int
"""
if(n == 1 or n == 0):
return 1
elif n==2:
return 2
elif n==3:
return 4
else:
# 假如不是以类的形式, 直接 return 函数() 不需要加 self.
return climbStairs(n-1) + climbStairs(n-2)+ climbStairs(n-3)
if __name__=='__main__':
n = int(input('Please give a number:'))
#sol=Solution(n)
print(climbStairs(n))
解法5
def climbStairs(n):
"""
:type n: int
:rtype: int
"""
temp = [1, 1,2,4]
result = 0
if n <= 2:
return n
elif n==3:
return 4
else:
while(n > 3):
result = temp[-1] + temp[-2] + temp[-3]
temp.append(result)
n = n - 1
return result
if __name__=='__main__':
n = int(input('Please give a number:'))
#sol=Solution(n)
print(climbStairs(n))
解法6
#记忆搜索
f = [-1] * 50
def fib(n):
if f[n] != -1:
return f[n]
if (n == 0 or n == 1):
return 1
elif n == 2:
return 2
elif n==3:
return 4
else:
f[n] = fib(n-1) + fib(n-2) + fib(n-3)
return f[n]
print(fib(4))
print(fib(5))
解法7
#递推 (动态规划思想)
f = [0] * 50
f[0] = 1
f[1] = 1
f[2] = 2
f[3] = 4
for i in range(4,50,1):
f[i] = f[i-1] + f[i-2] + f[i-3]
print(f[4])
print(f[5])
"""
一次可跳1、2、3级台阶,n级台阶有多少种跳法?最少跳几次?
"""
import itertools
def jumpfloor(n):
count=0
arr=[]
arr_sum=[]
for i in itertools.permutations(range(n),3):
if i[0]*1+i[1]*2+i[2]*3==n and i not in arr:
arr.append(i)
arr_sum.append(sum(i))
count += 1
minnum=min(arr_sum)
minnum_index=arr_sum.index(minnum)
min_cs = arr_sum[minnum_index]
min_zh = arr[minnum_index]
return arr,count,min_cs,min_zh
n=9
arr,count,min_cs,min_zh=jumpfloor(n)
print('跳法组合:{},共{}种跳法.最佳跳法:{},最佳跳法要跳{}次'.format(arr,count,min_zh,min_cs))
8.跳台阶
一只青蛙一次可以跳上1级台阶,也可以跳上2级。求该青蛙跳上一个n级的台阶总共有多少种跳法(先后次序不同算不同的结果)。
# -*- coding:utf-8 -*-
"""
理解为斐波那契数列
"""
class Solution:
def jumpFloor(self, number):
# write code here
if number <2:
return number
dp = [1,2]
for i in range(number-2):
dp.append(dp[-1]+dp[-2])
return dp[-1]
s=Solution()
s.jumpFloor(4)
import itertools
def jumpfloor(n):
count=0
arr=[]
arr_sum=[]
for i in itertools.permutations(range(n),2):
if i[0]*1+i[1]*2==n and i not in arr:
arr.append(i)
arr_sum.append(sum(i))
count += 1
minnum=min(arr_sum)
minnum_index=arr_sum.index(minnum)
min_cs = arr_sum[minnum_index]
min_zh = arr[minnum_index]
return arr,count,min_cs,min_zh
n=9
arr,count,min_cs,min_zh=jumpfloor(n)
print('跳法组合:{},共{}种跳法.最佳跳法:{},最佳跳法要跳{}次'.format(arr,count,min_zh,min_cs))
9.变态跳台阶
题目描述 一只青蛙一次可以跳上1级台阶,也可以跳上2级……它也可以跳上n级。求该青蛙跳上一个n级的台阶总共有多少种跳法。
# -*- coding:utf-8 -*-
class Solution:
def jumpFloorII(self, number):
# write code here
if number < 3:
return number
a = [0,1,2]
for i in range(3,number+1):
a.append(sum(a)+1)
return a[-1]
s=Solution()
s.jumpFloorII(4)