边工作边刷题:70天一遍leetcode: day 52-1
Coin Change
要点:一开始用了按amount循环的dp方法,结果对于大数,比如9936就TLE了。dp实际就是一种bottom up的方法(而recursion是top-down)。所以另一种dp方法就是把已经cover的值放到集合中,下一步从集合中取出每一个值更新后再加入集合。可以看出这是BFS。这样循环的次数只有达到目标需要的步数。
- 本质上说,dp vs. recursion和bfs vs. dfs是orthogonal的:前者是纵向的方向,后者是横向的方向。
- 最佳解法是从两边同时搜索,当然中间相遇处要用intersection
错误点
- bfs不能只将队头元素取出就进入下一循环(or 下一步)。而是要同时把本层元素全部遍历
- python的set初始化要用list作为输入,而不是一个元素
class Solution(object):
def coinChange(self, coins, amount):
"""
:type coins: List[int]
:type amount: int
:rtype: int
"""
sums = collections.deque([0])
visited = set()
step = 0
while amount not in sums and min(sums)<amount:
n = len(sums)
for i in xrange(n):
cur = sums.popleft()
for c in coins:
if cur+c not in visited:
visited.add(cur+c)
sums.append(cur+c)
step+=1
# print sums, visited, step
return step if amount in sums else -1