我花了一整晚的时间来制作这个食谱。这是我的第一个Python装饰师。我觉得我现在对装饰师的工作方式有了充分的理解,我想我想出了一个很好的面向对象的算法来自动提供回忆录。请告诉我你的想法。
粘贴在这里后,我做了一些快速的更改,所以如果我的更改损坏了什么,请告诉我(手边没有解释器)。
"""This provides a way of automatically memoizing a function. Using this eliminates the need for extra code. Below is an example of how it would be used on a recursive Fibonacci sequence function:
def fib(n):
if n in (0, 1): return n
return fib(n - 1) + fib(n - 2)
fib = memoize(fib)
That's all there is to it. That is nearly identical to the following:
_memos = {}
def fib(n):
if n in _memos:
return _memos[n]
if n in (0, 1):
_memos[n] = n
return _memos[n]
_memos[n] = fib(n - 1) + fib(n - 2)
return _memos[n]
The above is much more difficult to read than the first method. To make things even simpler, one can use the memoize function as a decorator like so:
@memoize
def fib(n):
if n in (0, 1): return n
return fib(n - 1) + fib(n - 2)
Both the first and third solutions are completely identical. However, the latter is recommended due to its elegance. Also, note that functions using keywords will purposely not work. This is because this memoization algorithm does not store keywords with the memos as it HEAVILY increases the CPU load. If you still want this functionality, please implement it at your own risk."""
class memoize:
"""Gives the class it's core functionality."""
def __call__(self, *args):
if args not in self._memos:
self._memos[args] = self._function(*args)
return self._memos[args]
def __init__(self, function):
self._memos = {}
self._function = function
# Please don't ask me to implement a get_memo(*args) function.
"""Indicated the existence of a particular memo given specific arguments."""
def has_memo(self, *args):
return args in self._memos
"""Returns a dictionary of all the memos."""
@property
def memos(self):
return self._memos.copy()
"""Remove a particular memo given specific arguments. This is particularly useful if the particular memo is no longer correct."""
def remove_memo(self, *args):
del self._memos[args]
"""Removes all memos. This is particularly useful if something that affects the output has changed."""
def remove_memos(self):
self._memos.clear()
"""Set a particular memo. This is particularly useful to eliminate double-checking of base cases. Beware, think twice before using this."""
def set_memo(self, args, value):
self._memos[args] = value
"""Set multiple memos. This is particular useful to eliminate double-checking of base cases. Beware, think twice before using this."""
def set_memos(self, map_of_memos):
self._memos.update(map_of_memos)发布于 2012-03-01 11:47:28
首先想到的是查看代码:样式。
将文档字符串置于函数之上而不是下面有一个特殊的原因?您所做的方式将在None属性中显示__doc__。
IMHO中的一些字符串甚至不是doc-string:
def __call__(self,*args)“”使类具有其核心功能。
这并不能说明什么。还请记住,注释是给程序员的,docstring是给用户的。
而且,我不太喜欢您将__call__方法放在__init__之前,但我不知道这是我自己,还是有一些约定。
澄清了这一点,我未能在您的所有方法中创建除__init__和__call__之外的所有方法。他们有什么用?你的代码在哪里使用它们?
如果你需要什么东西,那就不要写代码,否则你就会写一些你不需要的东西,这可能不符合你对明天的假设要求。
我知道您可能在做一个关于装饰师的练习,但是在实现某些东西时,不要仅仅为了它而编写代码。
让我们更深入地了解一下您的非文档字符串,如以下所示:
“删除所有备忘录。如果影响输出的内容发生了变化,这尤其有用。”def remove_memos(self):self._memos.clear()
这大概应该是:
def remove_memos(self):
"""Removes all memos."""
self._memos.clear()仅此而已。究竟做了什么“如果影响产出的东西发生了变化,这就特别有用。”这意味着?“影响输出的东西已经改变了”?这一切都很奇怪和混乱。另外,你的装饰师如何知道“影响输出的东西已经改变了”?
这里什么都没有:
def __call__(self,* args ):如果args不在self._memos中: self._memos参数 = self._function(*args)返回self._memos参数
这样做或使用任何其他方法。而且,您似乎无法提供可能使用它们的场景(即使可以,也无法使用它们)。
我的观点是,所有这些额外的方法都是无用的,如果您学习了一些Python,可能并不是编写它们,但这就是它们的使用范围内的问题。
发布于 2012-02-29 08:28:07
"""Gives the class it's core functionality."""
def __call__(self, *args):
if args not in self._memos:
self._memos[args] = self._function(*args)
return self._memos[args]“请求原谅而不是请求许可”更惯用(也更快),例如:
def __call__(self, *args):
try:
return self._memos[args]
except KeyError:
value = self._function(*args)
self._memos[args] = value
return valuehttps://codereview.stackexchange.com/questions/9538
复制相似问题