mqyqingfeng / Blog

冴羽写博客的地方,预计写四个系列:JavaScript深入系列、JavaScript专题系列、ES6系列、React系列。
30.53k stars 4.7k forks source link

大佬,我想请问一下,这个我写的过程是对的吗?checkscope执行的时候,return f 这个不太理解 #257

Open zehyan opened 2 years ago

zehyan commented 2 years ago
var scope = "global scope";
function checkscope(){
    var scope = "local scope";
    function f(){
        return scope;
    }
    return f;
}
checkscope()();

  1. 执行全局代码,创建全局执行上下文,全局上下文被压入执行上下文栈
    ECStack=[
    globalContext
    ]
  2. 全局上下文初始化
    globalContext={
    VO:[global],   //变量对象
    Scope:[globalContext.VO],// 作用域链
    this:globalContext.VO    // this指向的是全局
    }

    2.1 初始化的时候,checkscope函数被创建,保存父变量到自己函的内部属性[[scope]]

    checkscope.[[scope]]=[
    globalContext.VO
    ]

    3.执行checkscope函数,创建checkscope函数执行上下文,checkscope函数执行上下文被压入上下文执行栈

    ECStack=[
    checkscopeContext//checkscope函数执行上下
    globalContext //全局执行上下文
    ]

    4.checkscope函数执行上下文初始化: ● 1.复制函数的[[scope]]属性创建作用域链 ● 2.用arguments创建活动对象 ● 3.初始化活动对象,包括加入形参、函数声明,变量声明等 ● 4.将活动对象压入chekscope作用域链顶端

    checkscopeContext={
    AO:{//活动对象
      arguments:{
        length:0
      },
      scope:undefined,
      f:reference to function f(){}//函数f的引用
    }
    Scope:[AO,globalContext.VO],
    this:undefined,
    }

    ● 5.f函数被创建,创建f函数的执行上下文,并把f的执行上下文加入到执行上下文栈

    ECStack=[
    fContext,
    checkscopeContext//checkscope函数执行上下
    globalContext //全局执行上下文
    ]

    5.f的执行上下文初始化

    fContext={
    AO={
      arguments:{
        length:0
      }
    }
    Scope:[AO,checkscopeContext.VO,globalContext.VO],
    this:undefined,
    }

    6.checkscope函数执行,先执行fcontext出栈 ,然后返回f(){return scope},,然后再执行f(),结果是localscope

mqyqingfeng commented 2 years ago

@zehyan 你可以用这个地址 https://www.jsv9000.app/ 模拟一下执行栈的情况,我理解 checkscope执行完,就返回了一个变量,只是这个变量是一个函数而已,然后就出栈了,然后才是 f 函数入栈