Clojure 的“memoize”函数在缓存慢速 sql 查询和复杂计算方面有用吗?
Does Clojure's `memoize` function useful in caching slow sql queries and complex computations?
我的项目有一个 mysql 数据库和一个由 Clojure 编写的后端。
有些table的数据库每天只更新一次,要查询最新的
我们将使用的信息。
但是:
数据库很大,网络很慢,每次查询都会
花点时间。
我们需要在每次查询后进行复杂的计算。
我们需要进行多种 sql 查询,因此保存每个 sql 查询的结果是不现实的。
我们需要经常更改计算函数
调试的目的。
在慢 sql 查询的情况下,现在所有事情对我们来说都太慢了。
幸运的是,我们的数据每天只会更新一次,而且我们对数据库的一些查询非常频繁。
所以我们要缓存经常使用的 sql 查询和中间结果。
Clojure 的 memoize
功能对这类工作有用吗?我担心 sql 查询不是纯粹的,所以 memoize
不应该缓存它们的结果。但是有一天,我们 sql 查询的结果必须相同。
那么我可以 memoize
一天的结果并在第二天自动更新结果吗?
感谢您的帮助!
您应该为此使用缓存,例如。 G。 clojure.core.cache.
澄清评论:记忆有助于纯函数:如果你的函数总是returns给定相同输入的相同输出,你可以在计算一次后存储它。
如果输出随时间发生变化,则需要做失效处理。带有失效的记忆(以及一些其他问题,例如记住的东西的大小)被称为 "caching"。
如果您使用记忆机制进行缓存,您实际上是在其上实现缓存。只用一个缓存库就省事多了。
在这种情况下,您需要实现 "invalidation at midnight" 之类的东西。请参阅 https://github.com/clojure/core.cache/wiki 了解如何操作。
编辑: 它可能看起来有点像这样(未经测试,自带 today
):
(defcache MidnightCache [cache dates]
CacheProtocol
(lookup [this key]
(lookup this key nil))
(lookup [this key not-found]
(if (has? this key)
(get cache key)
not-found))
(has? [this key]
(let [d (get dates key)]
(and d
(= d (today)))))
(hit [this key]
this)
(miss [this key new-value]
(MidnightCache. (assoc (dissoc cache key)
key new-value)
(assoc (dissoc dates key)
key (today))))
(evict [this key]
(MidnightCache. (dissoc cache key)
(dissoc dates key)))
(seed [this base]
(MidnightCache. base
(zipmap (keys base)
(iterate identity (today))))))
我的项目有一个 mysql 数据库和一个由 Clojure 编写的后端。
有些table的数据库每天只更新一次,要查询最新的 我们将使用的信息。
但是:
数据库很大,网络很慢,每次查询都会 花点时间。
我们需要在每次查询后进行复杂的计算。
我们需要进行多种 sql 查询,因此保存每个 sql 查询的结果是不现实的。
我们需要经常更改计算函数 调试的目的。
在慢 sql 查询的情况下,现在所有事情对我们来说都太慢了。
幸运的是,我们的数据每天只会更新一次,而且我们对数据库的一些查询非常频繁。
所以我们要缓存经常使用的 sql 查询和中间结果。
Clojure 的 memoize
功能对这类工作有用吗?我担心 sql 查询不是纯粹的,所以 memoize
不应该缓存它们的结果。但是有一天,我们 sql 查询的结果必须相同。
那么我可以 memoize
一天的结果并在第二天自动更新结果吗?
感谢您的帮助!
您应该为此使用缓存,例如。 G。 clojure.core.cache.
澄清评论:记忆有助于纯函数:如果你的函数总是returns给定相同输入的相同输出,你可以在计算一次后存储它。
如果输出随时间发生变化,则需要做失效处理。带有失效的记忆(以及一些其他问题,例如记住的东西的大小)被称为 "caching"。
如果您使用记忆机制进行缓存,您实际上是在其上实现缓存。只用一个缓存库就省事多了。
在这种情况下,您需要实现 "invalidation at midnight" 之类的东西。请参阅 https://github.com/clojure/core.cache/wiki 了解如何操作。
编辑: 它可能看起来有点像这样(未经测试,自带 today
):
(defcache MidnightCache [cache dates]
CacheProtocol
(lookup [this key]
(lookup this key nil))
(lookup [this key not-found]
(if (has? this key)
(get cache key)
not-found))
(has? [this key]
(let [d (get dates key)]
(and d
(= d (today)))))
(hit [this key]
this)
(miss [this key new-value]
(MidnightCache. (assoc (dissoc cache key)
key new-value)
(assoc (dissoc dates key)
key (today))))
(evict [this key]
(MidnightCache. (dissoc cache key)
(dissoc dates key)))
(seed [this base]
(MidnightCache. base
(zipmap (keys base)
(iterate identity (today))))))