闭包
是指内部函数可以访问外部函数的变量。当通过一个外部函数返回一个内部函数时,即使外部函数已经结束执行了,但是内部函数引用的外部函数的变量依然保存在
内存中
,我们就把这些变量的集合称为闭包
。简单来讲,在函数A中还有函数B,函数B调用了函数A中的变量,那么B就是函数A的变量。
function test(){
let num = 0
return function (){
num++
console.log(num)
}
}
let f = test ()
f() //1
f() //2
闭包的优点和缺点
优点:
- 缓存起来,将变量隐藏不被回收
- 实现柯里化,利用闭包特性完成柯里化
缺点:
- 消耗内存,闭包产生的变量无法销毁
- 性能问题,由于闭包的内部变量优先级高于外部变量,所以需要多查找作用域的一个层次,一定程度影响查找速度。
闭包中访问过的变量 什么时候被移除?
1.timer
(function autorun(){
let x = 1;
setTimeout(function log(){
console.log(x);
}, 10000);
})();
变量x将一直存活到定时器的回调执行
或者clearTimeout()
函数被调用。如果这里使用的是setInterval()
,那么变量x将存活到clearInterval()
被调用。
2.event
(function autorun(){
let x = 1;
$("#btn").on("click", function log(){
console.log(x);
});
})();
变量x将存活到该事件处理函数被移除
3.Ajax
(function autorun(){
let x = 1;
fetch("http://").then(function log(){
console.log(x);
});
})();
变量x将存活到接收后端返回的结果之后。
变量的生命周期完全取决于闭包函数的生命周期。被闭包引用的外部作用域中的变量一直存活到闭包函数被销毁。如果一个变量被多个闭包函数使用,那么知道所有闭包函数被垃圾回收之后,该变量才会被销毁。