解決問題的策略
一、知識概覽
本章首先引入了分治策略,之後重點介紹了找零兌換問題,分別講解了貪心策略,遞歸解法和動態規劃解法。
二、找零兌換問題
2.1遞歸解法
#找零兌換問題
##遞歸解法
def recMC(coinValueList,change):#硬幣體系和找零個數
minCoins=change
if change in coinValueList:#最小規模直接返回:正好等於某一硬幣的幣值
return 1
else:
for i in [c for c in coinValueList if c<=change]:
numCoins=1+recMC(coinValueList,change-i)
if numCoins<minCoins:
minCoins=numCoins
return minCoins
import time
print(time.clock())
print(recMC([1,5,10,20,50,100],63))
print(time.clock())
輸出
3e-07
5
17.6337922
這種解法存在大量重複,非常費時
2.2遞歸解法優化
下面採用記錄最優解的方式優化遞歸解法
##改進代碼
def recDC(coinValueList,change,knownResults):#硬幣體系和找零個數
minCoins=change
if change in coinValueList:#最小規模直接返回:正好等於某一硬幣的幣值
knownResults[change]=1#記錄最優解
return 1
elif knownResults[change]>0:
return knownResults[change]#查表成功,直接用最優解
else:
for i in [c for c in coinValueList if c<=change]:
numCoins=1+recDC(coinValueList,change-i,knownResults)
if numCoins<minCoins:
minCoins=numCoins
knownResults[change]=minCoins#最優解記錄到表中
return minCoins
memo=[0]*64
print(time.clock())
print(recDC([1,5,10,20,50,100],63,memo))
print(time.clock())
print(memo)
輸出
17.6338019
5
17.6339165
[0, 1, 0, 0, 0, 1, 2, 3, 4, 5, 1, 2, 3, 4, 5, 2, 3, 4, 5, 6, 1, 2, 3, 4, 5, 2, 3, 4, 5, 6, 2, 3, 4, 5, 6, 3, 4, 5, 6, 7, 2, 3, 4, 5, 6, 3, 4, 5, 6, 7, 1, 2, 3, 4, 5, 2, 3, 4, 5, 6, 2, 3, 4, 5]
可以看到速度有了極大提升