1️⃣什么是缓存函数?
接收一个函数,用闭包将每次函数执行的结果缓存起来
2️⃣缓存函数的应用场景
例子1:求1到n的和优化
const add = (n) => {
console.log('执行了一次');
if (n === 1) {
return 1;
}
return add(n - 1) + n;
};
const addFn = memoize(add);
console.log(addFn(3)); // 执行3次
console.log(addFn(3)); // 不会执行 缓存里有结果了 直接取
const useAdd = () => {
const cache = {};
const add = (n) => {
console.log('执行了', cache);
if (n === 1) {
return 1;
}
return cache[n] || (cache[n] = add(n - 1) + n); // 如果缓存有值取缓存,否则继续递归存入缓存
};
return add;
};
const add = useAdd();
console.log(add(3)); // 会调用3次
console.log(add(2)); // 2已经缓存过了 所以只调用一次 从缓存中取
例子2:求斐波那契数列优化
// 不死神兔用闭包缓存优化
const useGetRabbit = () => {
const cache = {};
return function getRabbit(n) {
if (n === 1 || n === 2) {
return 1; // 出生后第三个月开始每个月才会生一对兔子,第三个月之前还是1对
}
return cache[n] || (cache[n] = getRabbit(n - 1) + getRabbit(n - 2)); // 如果缓存有就取缓存 否则当前月兔子对数取前两个月之和
};
};
const getRabbit = useGetRabbit();
console.log(getRabbit(48)); // 如果不用闭包缓存48个月就算不出来报栈溢出错误了
缓存函数:
const memoize = (fn) => {
const cache = {};
const func = (...args) => {
const key = JSON.stringify(args); // 函数入参序列化成string做为本次递归结果的唯一标识
return cache[key] || (cache[key] = fn.apply(null, args)); // 如果缓存中有则直接返回 否则执行本次递归并将结果和key存入缓存
};
return func;
};
总结:利用闭包及纯函数的特性来缓存函数每次调用的结果提高性能,避免重复的计算,使用时要注意一定要是个纯函数!