ここからメモ化デコレータのために(doctestを持つ)受け入れ答えを使用する:What can be done to speed up this memoization decorator?これらのメソッドコールのタイミングに大きな違いが生じる原因は何ですか?
、次のコード(fib.py):
class O(object):
def nfib(self,n): # non-memoized fib fn
if n in (0, 1):
return n
return self.nfib(n-1) + self.nfib(n-2)
@Memoized
def fib(self,n): # memoized fib fn
if n in (0, 1):
return n
return self.fib(n-1) + self.fib(n-2)
if __name__ == '__main__':
import time
o = O()
stime = time.time()
print "starting non-memoized"
for i in range(10):
print o.nfib(32)
print "finished non-memoized - elapsed secs =", time.time() - stime
stime = time.time()
print "starting memoized"
for i in range(10):
print o.fib(32)
print "finished memoized - elapsed secs =", time.time() - stime
stime = time.time()
print "starting memoized with reset"
for i in range(10):
Memoized.reset()
print o.fib(32)
print "finished memoized with reset - elapsed secs =", time.time() - stime
私は次のような出力が得られます。
C:\TEMP>python fib.py
starting non-memoized
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
finished non-memoized - elapsed secs = 16.4189999104
starting memoized
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
finished memoized - elapsed secs = 0.00100016593933
starting memoized with reset
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
2178309
finished memoized with reset - elapsed secs = 0.00299978256226
C:\TEMP>
私は3番目のループが最初のループの長さになると予想していました。なぜなら、ループを通過するたびにキャッシュがリセットされるからです。 fibメソッドにデバッグステートメントを挿入すると、キャッシュされていないことが示され、実際には3番目のループで結果が計算されますが、最初のループよりもはるかに高速です。なぜ???
私は恥ずかしがっていることを見落としてしまったと思っていますが、私の好奇心は現在私の誇りを上回っています。 (私は、Windows 7のプロマシンで64ビットのPython 2.7を使用しています)。
ありがとう。
私はこのコメントを前に説明しました。キャッシュはO(n^2)関数をO(n)にします。 –
@グレン:...はい、あなたは(あなたは不明ではありませんでした)...私はちょうど "それを"得ていませんでした。 ...デバッグステートメントを挿入してfib(覚えていない)の呼び出しを印刷し、2ギガバイトのファイルで終了し、毎回すべての呼び出し引数を表示する - 私は今すぐ "取得"!デコレータにもう一度感謝します。 – Gerrat