2016-07-26 48 views
6

我想使用memoize,但我担心缓存会无限增长,直到发生悲伤时间。缺省lodash memoize函数是否会造成内存泄漏?

我通过google/stackoverflow搜索找不到任何东西。

P.S.我正在使用lodash v4。

+0

它不会:它完全按照预期工作。如果你想“刷新”缓存 - 只需重新创建一个包装函数。这是因为你故意自愿存储所有数据。 – zerkms

+1

您也可以使用WeakMap作为您的缓存,如果它对您可用,并且您按对象键入。 – chardy

回答

3

简短回答是肯定的,lodash保留所有memoized数据,除非你指定不同的缓存类型。


默认的缓存是lodash的MapCache:
https://github.com/lodash/lodash/blob/4.14.0/lodash.js#L1968

的memoized值存储在根据密钥是否适合哈希(不同的数据结构和ES6地图是否是在可用环境):
https://github.com/lodash/lodash/blob/4.14.0/lodash.js#L1987 https://github.com/lodash/lodash/blob/4.14.0/lodash.js#L5561

如果你看一下这些数据结构的“设置”的方法,你会发现没有provisi对像LRU等什么:
哈希#集:https://github.com/lodash/lodash/blob/4.14.0/lodash.js#L1832
ListCache#集:https://github.com/lodash/lodash/blob/4.14.0/lodash.js#L1940
地图#集:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Map/set

+0

LRU将打破memoization的整个概念,并打破它的合同。 – zerkms

+1

过去,我使用带LRU的memoizee(“max”选项)作为缓存昂贵渲染输出的便捷方式。在那个特定的应用程序中,我获得了批量的匹配输入到我的函数,但随着时间的推移输入会改变。缓存未命中比不咀嚼内存更重要。 – chardy

+0

我已经接受了这一点,尽管我可能错过了内存泄漏术语,但这个答案确实是我所寻找的核心。 – ctrlplusb

4

简短的回答是否定的。

当您使用memoize功能,用户已接受合同:

  1. 该功能仅会被给定的参数
  2. 缓存保持在那里,只要有必要保证#调用1 (永远)

所以只有永久保存数据的实现才能符合要求。

什么是经常混淆 - 是一个“内存泄漏”的事情,只是“低效”使用内存。

在这种情况下 - 如果这对您是个问题,那么您有责任在适合您的算法时重新创建memoized函数。因为只有你知道什么时候这样做是安全的,而且不能自动完成。

+0

太好了,我想我只是误用了内存泄漏这个词。我的关切实际上是过度消费的记忆。猜猜这里的意思略有不同。谢谢 – ctrlplusb

+1

因此,最后我使用了一个名为'reselect'的库,它将响应我的应用程序状态(我正在使用react/redux)中的更改,然后输出memoized函数。我认为这符合你的建议。我还必须提供自己的memoize解析器,因为我正在使用该函数的多个参数。单元测试正在工作。谢谢! – ctrlplusb