我正在为Groovy语言编写一些培训材料,我正在准备一个可以解释Closures的例子。
该示例是“昂贵”方法的简单缓存闭包withCache
def expensiveMethod( Long a ) {
withCache (a) {
sleep(rnd())
a*5
}
}
所以,现在我的问题是:以下两个实现中哪一个在Groovy中是最快且更惯用的?
def withCache = {key, Closure operation ->
if (!cacheMap.containsKey(key)) {
cacheMap.put(key, operation())
}
cacheMap.get(key)
}
或
def withCache = {key, Closure operation ->
def cached = cacheMap.get(key)
if (cached) return cached
def res = operation()
cacheMap.put(key, res)
res
}
我更喜欢第一个例子,因为它不使用任何变量,但我想知道访问get
的{{1}}方法是否比返回包含计算结果的变量慢。
显然答案是“这取决于Map
的大小”,但出于好奇,我想得到社区的意见。
谢谢!
答案 0 :(得分:1)
首先,我同意OverZealous,担心两次获取操作是不成熟的优化。第二个例子也不等于第一个例子。例如,第一个允许null,而第二个允许在if中使用Groovy-Truth,这意味着null evals为false,例如空列表/数组/映射。因此,如果你想显示调用Closure,我会选择第一个。如果你想要一些更惯用的东西,我会为你的情况做这件事:
def expensiveMethod( Long a ) {
sleep(rnd())
a*5
}
def cache = [:].withDefault this.&expensiveMethod