持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第5天,点击查看活动详情
一、题目描述:
70. 爬楼梯 - 力扣(LeetCode) (leetcode-cn.com)
假设你正在爬楼梯。需要 n 阶你才能到达楼顶。
每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢?
示例 1:
输入:n = 2
输出:2
解释:有两种方法可以爬到楼顶。
1. 阶 + 1 阶
2. 阶
示例 2:
输入:n = 3
输出:3
解释:有三种方法可以爬到楼顶。
1. 1 阶 + 1 阶 + 1 阶
2. 1 阶 + 2 阶
3. 2 阶 + 1 阶
提示:
- 1 <= n <= 45
二、思路分析:
此题使用递归算法求解。
在递归的时候,会大量计算重复的数值,如当n=4时,在递归的过程中,会计算dfs(3)+dfs(2),此时会把dfs(3)和dfs(2)的情况重新再计算一遍,当数值越大,这种重复性工作急剧增长,造成很高的时间复杂度,详细的时间复杂度,可看官方题解,数学不好,只知道很大,运行超时了。
通过使用一个map的哈希表,保存每一个n的求值结果,通过空间来换取时间,改进后的递归算法,加入多一个map参数,用来保存每次n的计算结果,从而降低时间复杂度,这个时间复杂度好计算,等于O(n),因为有n个数就会计算n次,不存在重复计算的情况。
三、AC 代码:
func climbStairs(n int) int {
retArray := make(map[int]int)
return dfsMemory(n,retArray)
}
func dfsMemory(n int,m map[int]int) int {
if m[n] != 0{
return m[n]
}
if n == 0 || n == 1 {
return 1
}
m[n]=dfsMemory(n-1,m) + dfsMemory(n-2,m)
return m[n]
}
四、总结:
其实这个问题可以直接简化成斐波那契数列,也就是F(n) = F(n-1) + F(n-2)
我们可以用递归实现,但是用于过程中存在许多重复计算,因此最朴实的递归可能是超时了。所以需要定义一个备忘录,将一些计算过的值记录下来。
另外一种方法就是利用递推公式,每次保留两个状态,不断的往后计算