0
我已經實現了一個memoize
裝飾器,它允許緩存一個函數。緩存鍵包含函數參數。同樣,裝飾器緩存一個函數,但忽略參數。下面是代碼:裝飾重新使用另一個裝飾器的實現
class ApplicationCache (Memcached):
的make_key
方法:UltraJSON迅速提供了一個字符串,它SHA512散列成脆六角消化:
def make_key (self, *args, **kwargs):
kwargs.update (dict (enumerate (args)))
string = ujson.encode (sorted (kwargs.items()))
hashed = hashlib.sha512 (string)
return hashed.hexdigest()
的memoize
裝飾:因爲Python 2。 x吸吮wrt完全合格的函數名,我只是強迫用戶提供一個合理的name
:
def memoize (self, name, timeout=None):
assert name
def decorator (fn):
@functools.wraps (fn)
def decorated (*args, **kwargs):
key = self.make_key (name, *args, **kwargs)
cached = self.get (key)
if cached is None:
cached = fn (*args, **kwargs)
self.set (key, cached, timeout=timeout)
return cached
return decorated
return decorator
的cached
裝飾:它是memoize
幾乎逐字複製與單例外,make_key
忽略的參數:
def cached (self, name, timeout=None):
assert name
def decorator (fn):
@functools.wraps (fn)
def decorated (*args, **kwargs):
key = self.make_key (name) ## no args!
cached = self.get (key)
if cached is None:
cached = fn (*args, **kwargs)
self.set (key, cached, timeout=timeout)
return cached
return decorated
return decorator
現在,我的問題cached
是,它尖叫重新因子:它應該使用memoize
和想法將消除fn
(使用functools.partial
也許?),如:
def cached (self, name, timeout=None):
## Reuse the more general `memoize` to cache a function,
## but only based on its name (ignoring the arguments)
實際上,我不知道如果我在這裏多事了DRY原則,如果重複使用,甚至有可能,因爲目前執行的cached
忽略的參數同時建立唯一鍵(但在調用裝飾函數時明顯是而不是)。
輝煌,與裝飾工作必須我睜不開眼這個明顯的解決方案。謝謝。 ; D的要點可在這裏:https://gist.github.com/4417820 – hsk81
@ hsk81:順便說一句,你爲什麼使用JSON串參數?只需要執行'str()'可能會更好,因爲這樣會更快,並且可以用於不可序列化的對象。 – Blender
謝謝你是對的,用'unicode'替換'JSON.encode'(使用會話ID'sid'而不是會話);更新的要點可在https://gist.github.com/4418107獲取。 – hsk81