作用域链

  • VO: variable object
  • AO: active object
    在讲闭包之前,咱们得先讲讲作用域链,因为闭包的先决条件就是作用域链的存在。

    var color = 'red'function isRed() {  return color === 'red'}console.log(isRed()) // true 

    大家都晓得因为作用域链,咱们能够拜访到流动对象(全局对象)上的属性,但其中的原理是什么呢?

  1. 首先: 浏览器在预编译阶段会创立一个 VO 对象, VO 对象中会蕴含全局的办法以及属性,如果遇到办法会给办法的[[Scope]]传递以后的作用域链(scope chain),作用域链决定了上下文以及函数的执行程序。
  2. 解析实现之后,面临的就是执行 isRed 办法,在执行该办法时,浏览器会给以后函数创立一个 AO 对象,在 AO 对象中, 它的this指向 window(严格模式为undefined), 同时会 return 一个 value。

闭包

讲完作用域链,就到咱们的正题,闭包。
在调用函数时,浏览器会给函数创立一个执行高低问,并创立一个执行上下文,并创立作用域链。当咱们有函数嵌套,并且内函数援用了外函数的变量就会产生闭包。但产生闭包的原理呢?间接上代码!!!

function myClosure() {    var a = 1     return function () {        ++a        return a    }}var myclosure = myClosure()console.log(myclosure()) //2console.log(myclosure()) //3
  1. 首先,浏览器在预编译阶段会创立一个 VO 对象, VO 对象中会蕴含全局的办法以及属性,如果遇到办法会给办法的[[Scope]]传递以后的作用域链(scope chain),作用域链决定了上下文以及函数的执行程序。
  2. 执行 myClosure 办法,创立 AO 对象,在 AO 对象中, 它的this指向 window, 同时会 return 一个 value,因为return 的是一个function, 所以在预编译阶段,会把该办法的[[Scope]]预装上以后的作用域链,即全局上下文myClosure的函数上下文。
  3. 执行 myclosure 办法,创立 myclosure 的 AO 对象,该对象的this指向window,同时因为应用了myClosure函数的 AO 对象,所以在内存中保留着对该变量的援用(Closure 指向了myClosure),因而myClosure在被执行实现后应该被销毁的函数上下文并没有被销毁。就此,产生了闭包。

以上内容,是我联合书本和实际,了解必定有不到位甚至错的中央,欢送各位大佬的点评!!!