JavaScript的闭包
官方对闭包的解释是:一个拥有许多变量和绑定了这些变量的环境的表达式(通常是一个函数),因而这些变量也是该表达式的一部分。
不理解不要紧,先来一个简单的闭包
function funA(){
let a = 857;
return function funB(){
let b = a;
return b;
}
}
let A = funA();
let B = A();
console.log(B);
我们看到打印的结果是函数funA
中的变量,我们通过函数funB
的返回值,在函数funA
的外部调用使用了函数funA
的局部作用域变量。
函数程序的执行,都是在执行空间中执行,函数执行结束,执行空间被销毁,变量等,也会被销毁,所以函数局部作用域中的变量,无法在函数外部被调用,这时我们可以通过闭包让函数中的变量都被保存在内存中。
总结一下:
通过建立一个不被销毁的存储空间,来在函数的外部调用和使用函数内部的数据
闭包的应用
<ul>
<li>我是第一个li标签</li>
<li>我是第二个li标签</li>
<li>我是第三个li标签</li>
<li>我是第四个li标签</li>
<li>我是第五个li标签</li>
</ul>
let oLis = document.querySelectorAll('li');
for(var i = 0 ; i <= oLis.length-1 ; i++){
oLis[i].addEventListener('click' , (function(a){
return function(){
console.log(a);
}
})(i+1) );
//普通语法
/*oLis[i].addEventListener('click' ,function(){
console.log(i+1)
})*/
}
使用var
来定义变量i
;不使用闭包,使用普通语法执行点击事件,我们会看到打印的结果是5
,js执行首先会执行主线程,异步相关的会存到异步队列里,当主线程执行完毕开始执行异步队列, 主线程执行完毕后,i
的值为5
,所以打印的结果都是5
;这时我们就可以使用闭包,保留执行空间,也就是保留每次生成的i
的数值,执行点击事件时,可以执行到对应的i
的数值。