解题思路

  • 变量背包、作用域链、局部变量不销毁、函数体外访问函数的内部变量、内存泄漏、内存溢出、形成块级作用域、柯里化[1]、构造函数中定义特权方法、Vue中数据响应式Observer

标准回答

  • 一个函数和词法环境的引用捆绑在一起,这样的组合就是闭包(closure)。

  • 一般就是一个函数A,return其内部的函数B,被return出去的B函数能够在外部访问A函数内部的变量,这时候就形成了一个B函数的变量背包。A函数执行结束后这个变量背包也不会被销毁,并且这个变量背包在A函数外部只能通过B函数访问。

  • 闭包形成的原理:
    作用域链,当前作用域可以访问上级作用域中的变量

  • 闭包解决的问题:
    能够让函数作用域中的变量在函数执行结束之后不被销毁,同时也能在函数外部可以访问函数内部的局部变量。

  • 闭包带来的问题:
    由于垃圾回收器不会将闭包中变量销毁,于是就造成了内存泄露,内存泄露积累多了就容易导致内存溢出。

加分回答

  • 闭包的应用:能够模仿块级作用域,能够实现柯里化,在构造函数中定义特权方法、Vue中数据响应式Observer中使用闭包等。

讨论区

  • A函数可以访问B函数里面的变量,这种现象被称为闭包,一般用来防抖节流。滥用闭包可能会造成内存泄漏的问题。

  • 当一个函数A内部的另一个函数B被return出去,被return出去的B函数访问A中的变量时就会形成闭包。

  • 一个作用域可以访问另一个函数的变量就会产生闭包,而这个变量所在的函数就被称为闭包函数。

    1. 作用:延申了变量的作用范围。
    2. 坏处:滥用闭包会造成内存泄漏,不使用的变量也保存在内存里,从而消耗了大量内存,降低了浏览器的性能。
  • 闭包是一个A函数通过返回一个函数b,使得外部作用域可以通过函数b访问到A内部的参数和变量。因为浏览器的垃圾回收机制不会将闭包中的变量销毁,所以闭包使用不当可能会造成内存泄漏。

  • 由于在js中,变量的作用域属于函数的作用域在函数执行后如果没有引用值就会被回收,内存也会被随之回收,但是闭包存在一个函数内部的子函数,由于其可以访问上级作用域的原因,即使上级作用域函数执行完毕后,作用域内的值也不会被销毁。


【参考内容】: