JS执行上下文

hdc-web / 2024-10-29 / 原文

初始化全局对象 Global Object(GO)

◼ js引擎会在执行代码之前,会在(堆内存)中创建一个全局对象:Global Object(GO)
    该对象所有的作用域(scope)都可以访问;
    里面会包含Date、Array、String、Number、setTimeout、setInterval等等;
    其中还有一个window属性指向自己

执行上下文(Execution Contexts )

◼ js引擎内部有一个执行上下文栈(Execution Context Stack,简称ECS),它是用于执行代码的调用栈。
◼ 那么现在它要执行谁呢?执行的是全局的代码块:
    全局的代码块为了执行会构建一个Global Execution Context(GEC);
    GEC会被放入到ECS中执行;
◼ GEC被放入到ECS中里面包含两部分内容:
    第一部分:在代码执行前,在parser转成AST的过程中,会将全局定义的变量、函数等加入到GlobalObject中,但是并不会赋值;
        ✓ 这个过程也称之为变量的作用域提升(hoisting)
    第二部分:在代码执行中,对变量赋值,或者执行其他的函数;

认识VO对象(Variable Object)

◼ 每一个执行上下文会关联一个VO(Variable Object,变量对象),变量和函数声明会被添加到这个VO对象中。
◼ 当全局代码被执行的时候,VO就是GO对象了

全局代码执行过程

全局代码执行:
创建一个执行上下文中会关联一个VO对象-----> 1.全局代码在执行之前会创建一个全局对象GO并且与VO关联--->2.GO记录的是所有被定义的全局变量的名称,他们的值都是undefined,并且全局对象里的函数如果有内容会优先创建一个函数的对象--->3.给变量进行赋值或者执行其他的函数

函数代码执行过程

在执行的过程中执行到一个函数时,就会根据函数体创建一个函数执行上下文(Functional Execution Context,简称FEC),并且压入到EC Stack中。
  ◼ 因为每个执行上下文都会关联一个VO,那么函数执行上下文关联的VO是什么呢?
      当进入一个函数执行上下文时,会创建一个AO对象(Activation Object);
      这个AO对象会使用arguments作为初始化,并且初始值是传入的参数;
      这个AO对象会作为执行上下文的VO来存放变量的初始化;
函数执行:
创建一个执行上下文VO----->创建一个AO对象,VO对象关联AO对象保存变量的名称,并且赋值为undefined---->AO对象使用argument作为初始化保存传入的形参---->为变量进行赋值---->执行完成会弹出--->继续执行全局执行上下文

作用域和作用域链

◼ 当进入到一个执行上下文时,执行上下文也会关联一个作用域链(Scope Chain)
    作用域链是一个对象列表,用于变量标识符的求值;
    当进入一个执行上下文时,这个作用域链被创建,并且根据代码类型,添加一系列的对象;

!!!作用域链是在定义的位置一层层往上找的和调用的位置没关系