目录
一、递归中的重复计算
# Python implementation
def fibonacci(n):
"""
:type n: int
:rtype: int
"""
if n < 2:
return n
else:
return fibonacci(n-1) + fibonacci(n-2)
def fib(self, N):
"""
:type N: int
:rtype: int
"""
cache = {}
def recur_fib(N):
if N in cache:
return cache[N]
if N < 2:
result = N
else:
result = recur_fib(N-1) + recur_fib(N-2)
# put result in cache for later reference.
cache[N] = result
return result
return recur_fib(N)
参考文献:https://leetcode-cn.com/explore/orignial/card/recursion-i/258/memorization/1211/
二、斐波那契数
2.1 题目要求
2.2 解决过程
个人实现
法一:无记忆递归。
2020/07/19 - 18.27% (800ms) - 最简单但低效的方法
class Solution:
def fib(self, N: int) -> int:
if N == 1:
return 1
if N == 0:
return 0
return self.fib(N-1) + self.fib(N-2)
法二:有记忆递归。使用字典 memory 来记忆计算过的结果,避免重复冗余的计算。
2020/07/19 - 53.74% (44ms) - 性能显著提升,但由于实现存在问题,未能发挥最佳效果 (对比官方法三)
class Solution:
def __init__(self):
self.memory = {0: 0, 1: 1} # 计算记录, 但其实这种方式效率并不高, 详见官方法三
def fib(self, N: int) -> int:
if N in self.memory:
return self.memory[N]
else:
self.memory[N] = self.fib(N-1) + self.fib(N-2) # 记忆
return self.memory[N]
官方实现与说明
class Solution:
def fib(self, N: int) -> int:
if N <= 1:
return N
return self.fib(N-1) + self.fib(N-2)
2020/07/19 - 12.98% (800ms)
class Solution:
def fib(self, N: int) -> int:
if N <= 1:
return N
return self.memoize(N)
def memoize(self, N: int) -> {}:
cache = {0: 0, 1: 1}
# Since range is exclusive and we want to include N, we need to put N+1.
for i in range(2, N+1):
cache[i] = cache[i-1] + cache[i-2]
return cache[N]
2020/07/19 - 73.37% (40ms)
## 这比个人实现二还要好, 注意对比 cache 的来源与差异
class Solution:
def fib(self, N: int) -> int:
if N <= 1:
return N
self.cache = {0: 0, 1: 1} # 比放在数据成员的个人实现法二要好
return self.memoize(N)
def memoize(self, N: int) -> {}:
if N in self.cache:
return self.cache[N]
self.cache[N] = self.memoize(N-1) + self.memoize(N-2)
return self.memo