闭包实现命名空间隔离,核心在于用函数作用域包裹私有变量和函数,并只暴露有限接口,使内部状态不被外部直接访问或修改;依赖函数作用域天然隔离、支持多模块互不干扰、允许初始化与私有工具函数、可通过工厂函数创建多实例。

靠函数作用域天然隔开变量
JavaScript 中函数是创建独立作用域的最小单位。闭包利用这一点,在函数内部声明变量和辅助函数,它们默认不会跑到全局去:比如这样写:
(function() {
const config = { apiBase: 'https://api.example.com' };
function request(url) { return fetch(config.apiBase + url); }
window.ApiClient = {
get: (path) => request(path)
};
})();
config 和 request 只在自执行函数内有效,外部既不能读取 config,也不能调用 request——只有 ApiClient.get 是唯一出口。
多个模块互不干扰
每个闭包拥有独立的词法环境,即使变量名相同也不会冲突:- 计数器模块 A:内部用 count = 0,每次调用 inc 都累加自己的 count
- 计数器模块 B:也用 count = 100,但它的 count 和 A 完全无关
不需要手动加前缀(如 counterA_count),闭包自动完成“同名不同体”的隔离。
支持初始化和私有工具函数
模块不只是存数据,还能做一次性设置、封装校验逻辑等:- IIFE 开头可加载默认配置、绑定事件、预请求资源
- 定义仅内部使用的格式化函数、权限检查函数,不对外暴露
- 私有变量可以是对象、数组、DOM 引用,只要不 return 出去就安全
工厂函数支持多实例
如果需要多个独立模块(比如多个表单验证器),把闭包包装成函数:function createValidator(rules) {
const errors = [];
function validate(data) {
errors.length = 0;
for (let rule of rules) {
if (!rule.test(data)) errors.push(rule.msg);
}
return errors.length === 0;
}
return { validate, getErrors: () => [...errors] };
}
const loginValidator = createValidator([...]);
const registerValidator = createValidator([...]);
两个实例各自维护 errors 数组,彼此完全隔离。
不复杂但容易忽略。

















