闭包是JavaScript实现函数记忆的核心机制,通过保存外部变量作为缓存容器(如Map),使内部函数能查缓存、计算并存储结果;键常由JSON.stringify(args)生成,但需注意引用类型限制。

闭包是 JavaScript 中实现函数记忆(Memoization)的核心机制,它让函数能“记住”之前的计算结果,避免重复执行耗时操作。
缓存逻辑依赖闭包保存记忆表
闭包使内部函数可以访问并持久化外部函数的局部变量,比如一个对象或 Map 作为缓存容器。每次调用带记忆的函数时,先查缓存,命中则直接返回;未命中则计算、存入缓存再返回。
- 缓存容器通常用 Object(适合字符串/数字键)或 Map(支持任意类型键,如对象、函数)
- 键生成需稳定:对参数做 JSON.stringify 或自定义序列化,确保相同输入总产生相同键
- 注意引用类型参数:直接用
JSON.stringify(args)可能忽略函数、undefined、Symbol 等,简单场景够用,复杂场景建议用专用序列化库或限制参数类型
基础版 memoize 函数写法
一个通用、轻量的 memoize 工具函数,接收目标函数,返回带缓存能力的新函数:
function memoize(fn) {
const cache = new Map();
return function(...args) {
const key = JSON.stringify(args);
if (cache.has(key)) {
return cache.get(key);
}
const result = fn.apply(this, args);
cache.set(key, result);
return result;
};
}使用示例:
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
立即学习“Java免费学习笔记(深入)”;
const fib = memoize(n => n <= 1 ? n : fib(n - 1) + fib(n - 2)); console.log(fib(10)); // 快速计算,后续调用复用结果
支持 this 和多参数的健壮版本
原生 JSON.stringify 无法处理函数、正则、Date 等,且不保留 this 上下文。实际项目中可增强:
- 用 WeakMap 缓存绑定到特定
this的结果(适合方法记忆) - 对参数做更安全的键生成:例如只允许原始值和普通对象,跳过不可序列化值并警告
- 添加最大缓存条数或 LRU 清理策略,防止内存泄漏
- 暴露
clear()方法方便手动重置缓存
注意点与适用边界
函数记忆不是万能优化手段:
- 仅适用于纯函数(相同输入必得相同输出,无副作用),否则缓存结果可能出错
- 参数频繁变化或几乎不重复时,缓存反而增加开销和内存占用
- 异步函数不能直接 memoize,需配合 Promise 缓存(缓存的是 Promise 实例,避免并发重复请求)
- 全局共享缓存需谨慎,不同调用方可能因
this或闭包环境不同而误共享结果

















