/**
*闭包浅析
* 我在书本上找到的对闭包的定义为:函数可以记住并访问所在的词法作用域时,就产生了闭包
* 不管以何种手段将内部函数传递到所在的词法作用域以外,都会持有对原始定义作用域的引用。无论在何处执行这个函数。都会使用闭包。
* 闭包就是能够读取其他函数内部变量的函数
*/
function fun(){
var a = 2;
function fun1(){
a +=1;
console.log(a)
}
fun1();
}
fun();//3
/**
*上面这个代码是闭包么?可以说他不完全是一个闭包,但是却涵盖了闭包最重要的部分
* 他记住并访问所在的词法作用域
*/
function bb(){
var a = 2;
function bb1(x){
a = a + x;
console.log(a);
}
return bb1;
}
var baz = bb();
var baz1 = bb(); // 创建的副本
baz(3);//5
baz(8);//13
baz1(2);
/**
*上面代码里,将bb1函数本身作为一个值进行传递, 在外部能够对内部函数的变量进行引用和改变
* bb1函数在自己定义的词法作用域以外的地方执行
* 在执行完bb()之后应该销毁bb()里的作用域,但是因为有bb1函数在引用着bb函数的作用域,所以不能够销毁
* baz(3)能够对变量a进行访问,就是最好的说明
* bb1依然持有对该词法作用域的引用,这个引用就叫做闭包
* 无论使用何种方式对函数类型的值进行传递,当函数在别处被调用时都可以观察到闭包
*/
function foo(){
var a = 2;
function baz(){
console.log(a);
}
bar(baz);
}
function bar(fn){
fn();//这就是闭包
}
/**
*函数的传递可以是间接的
*/
var fn;
function cc(){
var a = 2;
function cc1(){
console.log(a);
}
fn = cc1;
}
function cc2(){
fn();//这就是闭包
}
cc();
cc2();
/**
*回调函数都是闭包
*/
function dd(){
var message = '萨拉黑哟!'
function dd1(){
console.log(message);
}
setTimeout(dd1,1000)
}
dd();
/**
*dd的作用域在1000ms之后并没有被销毁,而是被访问了,因为dd1函数对message的引用一直都在
*/
/**
*总结一下,本质上无论何时何地,如果将函数当做第一级的值类型并到处传递,你就会看到闭包在这些函数中的应用
* 在定时器,事件监听器,ajax请求,跨窗口通信,web workers或者任何其他异步任务中,只要使用了回调函数,实际上就是在使用闭包
* 换句话说,一个函数的内部有一个函数在引用他所在的词法作用域,并且这个函数执行在定义它的作用域之外,就在使用闭包了
*/
/**
*IIFE并不是闭包(立即执行函数)
* 因为他并不是在他本身的词法作用域之外执行的,他在定义它的作用域中执行,就是通过普通的词法作用域查找并不是闭包发现的
*/
闭包浅析
最新推荐文章于 2024-03-06 15:34:46 发布