动态规划
动态规划 Dynamic Programming 一种设计的技巧,是解决一类问题的方法 dp遵循固定的思考流程:暴力递归 —— 递归+记忆化 —— 非递归的动态规划(状态定义+转移方程) 斐波那契数列 暴力递归,看上去很简洁 def fib(n): return n if n <= 1 else fib(n-1) + fib(n-2) 画出递归树分析一下,可以很容易发现有很多重复计算。 重叠子问题 。 递归算法的时间复杂度怎么计算? 子问题个数乘以解决一个子问题需要的时间。显然,斐波那契数列的递归解法时间复杂度为O(2 n * 1),暴力递归解法基本都会超时。 如何解决? 递归 + 记忆化 仍然使用递归,不同点在于,如果重叠子问题已经计算过,就不用再算了,相当于对冗余的递归树进行了剪枝。 由于不存在重叠子问题,时间复杂度为O(n * 1),降到线性。 1 class Solution: 2 def Fibonacci(self, n): 3 # write code here 4 if n <= 1: 5 return n 6 memo = [-1] * (n+1) 7 memo[0], memo[1]= 0, 1 8 9 def helper(n, memo): 10 if memo[n] >= 0: 11 return memo[n] 12 memo[n] = helper(n