【问题标题】:Is there an established memoize on-disk decorator for python?python 是否有已建立的 memoize 磁盘装饰器?
【发布时间】:2012-01-15 17:15:33
【问题描述】:

我一直在寻找一个 python 模块,它提供了一个具有以下功能的 memoize 装饰器:

  • 将缓存存储在磁盘上,以便在后续程序运行中重复使用。
  • 适用于任何可腌制的参数,最重要的是 numpy 数组。
  • (奖励)检查函数调用中的参数是否发生了变化。

我为这个任务找到了一些小代码sn-ps,并且可能自己实现一个,但我更喜欢为这个任务建立一个包。我还找到了incpy,但这似乎不适用于标准的 Python 解释器。

理想情况下,我希望在磁盘上有类似functools.lru_cache 的内容以及缓存存储。有人可以为我指出一个合适的包吗?

【问题讨论】:

标签: python decorator memoization


【解决方案1】:

我不知道有什么 memoize 装饰器可以处理所有这些,但你可能想看看 ZODB。这是一个建立在pickle 之上的持久性系统,它提供了一些附加功能,包括能够在不使用对象时将对象从内存移动到磁盘,以及仅保存已修改的对象。

编辑:作为评论的后续。 ZODB 不支持开箱即用的记忆装饰器。但是,我认为您可以:

  • 实现你自己的persistent class
  • 在您需要的方法中使用 memoization 装饰器(任何标准实现都应该可以工作,但可能需要对其进行修改以确保设置了 dirty bit

之后,如果您创建该类的对象并将其添加到 ZODB 数据库中,当您执行其中一个 memoized 方法时,该对象将被标记为脏,并且更改将在下一个事务中保存到数据库中提交操作。

【讨论】:

  • 感谢您的提示。所以看起来ZODB在灵活存储数据到内存或者磁盘方面还是相当不错的。但是,在记忆化的背景下,显着的优势是什么?
  • 所以我猜持久化类应该是定义了 memoization 装饰器的类,而 memoization 缓存将是该类的一个属性。我会在不久的将来尝试这个......
【解决方案2】:

我意识到这是一个有 2 年历史的问题,这不算是“成熟”的装饰师,但是……

这很简单,您真的不必担心只使用已建立的代码。模块的docs 链接到source,因为除了本身有用之外,它还可以用作示例代码。

那么,您需要添加什么?添加filename 参数。在运行时,将pickle.load 的文件名改成cache,如果失败则使用{}。添加一个cache_save 函数,它只是将pickle.saves 缓存到锁定下的文件中。将该函数附加到wrapper,与现有函数相同(cache_info 等)。

如果您想自动保存缓存,而不是将其留给调用者,这很容易;这只是什么时候这样做的问题。你想出的任何选项——atexit.register,添加一个save_every 参数,这样它就可以保存每一个save_every 未命中,......——实现起来都很简单。在this answer 中,我展示了它需要的工作量。或者您可以获得完整的工作版本(自定义或按原样使用)on GitHub

还有其他方法可以扩展它——在cache_info 中放置一些与保存相关的统计信息(上次保存时间、自上次保存后的命中和未命中……),复制缓存并将其保存在后台线程中,而不是将其内联保存等。但我想不出任何值得做的事情并不容易。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2010-12-15
    • 2015-05-12
    • 1970-01-01
    • 2015-08-23
    • 1970-01-01
    • 1970-01-01
    • 2017-02-04
    相关资源
    最近更新 更多