闭包--没有那么复杂!

一弄JS,就总有人在提闭包、闭包的,此前不了解,上网上搜,很多讲的也过于难懂,感觉没有必要那么复杂,今天就把我对于闭包的理解总结一下,力求简单、通俗、易懂


目录

1.什么是闭包

2.闭包有什么用?

3.闭包带来了什么问题呢?

4.总结


 1.什么是闭包

通俗的理解就是:子函数使用着父函数作用域内的变量,导致父函数作用域内的变量无法回收释放的这种情况。

<script>
function a(){
   let num=0;
   return ()=>{
     console.log(num++);
   }
};
let t=a();
//执行三次结果是多少?
t();
t();
t();
</script>

 看上面的代码,分别执行三次t(),那么结果是多少呢?

结果是0,1,2,这是怎么回事呢?原因就是闭包导致的。

我们首先分析:a函数内有一个num变量和一个子函数,在子函数中使用着父函数a的变量num,使其自加1。随后将a函数执行后复制给t,由于子函数一直在使用num变量(其实不论子函数是否使用,父函数的变量都不会释放,随时等待子函数调用除非子函数引用被释放),所以num变量并不会回收释放。也就是说三次t()改变的num其实是一个。这就是闭包的原因,如果没有闭包,在子函数处理完num后,num回收,则应该是三个0。

2.闭包有什么用?

从另一个角度理解,如果一个函数没有被回收释放,那么他的父级、父级的父级。。。。。祖宗级(全局)的变量也不会被释放,而且可以被函数访问到。这就是为什么全局变量在哪里都可以访问的原因了,其实就是闭包的应用。那什么时候全局变量不可用了呢,就是他内部的子函数引用都被清空的时候,也就是程序关闭了,网页关闭了之后。

1.绝大多数时候我们不会有意识的用到闭包,但是没有闭包你得程序是跑不了的,比如全局变量。。。。。

2.极少数情况下我们用函数去给一个变量“续命”。这种情况下,闭包就会被用到了。

3.还有就是,如果问你:

JS中没有严格意义的私有变量,请问你能弄出来绝对私有么?答案:能。请看代码:

<script>
  //这个num就是真的严格意义的私有
  let a=(function (){
    let num =0;
    return {
      get(){
        return num;
      },
      set(val){
        num=val;
      }
    }
  })();
  a.set(55);
  console.log(a.get());
</script>

这时a将返回一个json,里面有两个函数,分别是get和set。当你在外部给num赋值或者是调用num时,必须通过get和set“属性访问器”去访问,否则无法访问到num变量(真正的私有)。因为当你不用get和set时候也就是说get和set函数是不存在的,那么根据“闭包的原理”num会被释放掉,也就是说num不存在了,所以你直接num赋值是undefined的。

3.闭包带来了什么问题呢?

这里最为典型的就是for循环中用var定义循环变量(var i=0;i<10;i++),循环的结果是相同的,就是最后一次运算的结果。这里就涉及到了作用域和闭包的问题。详细的请看我的这篇文章,本文就不赘述了。

深入理解js_for循环条件中使用var为什么会出问题?(js块级作用域理解)

4.总结

相信大家看完之后一定会明白闭包是咋回事,这就是我目前理解道德闭包。当然如果有更好的补充,十分欢迎大家留言讨论。

评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

韦_恩

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值