var cache = {};
return function(){
var key = arguments.length + Array.prototype.join.call(arguments,',');
if(key in cache){
return cache[key];
}else{
return cache[key] = f.apply(this,arguments);
}
}
}
外部函数中有cache变量,在return的函数里面有对cache的引用,由于闭包的特点,cache变量保持了其持久性。返回的函数中存在一个key变量,key是由参数的长度和参数组成的字符串组合成的,保证了参数的唯一性。我们先创建一个示范的函数,计算最大公约数:
function gcd(a,b){
var t;
if(a<b) t=b,b=a,a=t;
while(b!=0){
t=b,b=a%b,a=t;
return a;
}
}
完整的代码如下:
function memorize(f){
var cache = {};
return function(){
var key = arguments.length + Array.prototype.join.call(arguments,',');
if(key in cache){
return cache[key];
}else{
return cache[key] = f.apply(this,arguments);
}
}
}
function gcd(a,b){
var t;
if(a<b) t=b,b=a,a=t;
while(b!=0){
t=b,b=a%b,a=t;
return a;
}
}
var gcdmemo = memorize(gcd);
gcdmemo(85,187);
gcdmemo(85,187);
第一次调用gcdmemo的时候,我们的程序计算出结果的同时,把参数的唯一标识和结果以key-value的方式保存到闭包中的变量cache中,于是第二次调用的时候,我们的' key in cache '是返回true的,达到了直接从内存中读取的目的。如果说这个例子意义不大,那我们看一个递归相关的:
var f = memorize(function(n){
return (n<=1)?1:n*f(n-1);
});
f(5);
上面的程序,当结果计算出来之后,4~1的值也存在我们的cache中,再次调用的时候我们就直接返回了记忆的值,达到使用内存空间来提高计算效率的效果。当然,这需要适合的场景才能使用,毕竟cache是占用着内存的。