什么是闭包?
当函数可以记住并访问所在的词法作用域时,就产生了闭包,即使函数是在当 前词法作用域之外执行。 ----《你不知道得JavaScript》
我们来看一段代码:
function fn1(){
var name = "zs";
function fn2(){
console.log(name);
}
return fn2;
}
var fn3 = fn1();
fn3();
这段代码十分清楚的展示了闭包
- fn2能访问fn1的作用域
- 把fn2作为返回值
- fn1执行后,讲fn2的引用赋值给了fn3
- 执行fn3,输出了fn1里面定义的变量name
一般来说,当函数执行完毕的时候会销毁自身的作用域AO,而闭包却将其执行完毕的作用域保留了下来。fn3依然可以访问该作用域的引用,这个就是闭包
闭包的应用
闭包的应用比较典型是定义模块,我们将操作函数暴露给外部,而细节隐藏在 模块内部:
function module() {
var arr = [];
function add(val) {
if (typeof val == 'number') {
arr.push(val);
}
}
function get(index) {
if (index < arr.length) {
return arr[index]
} else {
return null;
}
}
return {
add: add, get: get
}
}
var mod1 = module();
mod1.add(1);
mod1.add(2);
mod1.add(3);
console.log( mod1.get(2) );
闭包的缺点 : 闭包滥用会造成内存泄露,也就是闭包中引用到的包裹函数中定义的变量都永远不会被释放,所以我们应该在必要的时候,及时释放这个闭包函数。