乐趣区

关于javascript:JavaScript中闭包的原理

作用域链

  • 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()) //2
console.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 在被执行实现后应该被销毁的函数上下文并没有被销毁。就此,产生了闭包。

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

退出移动版