美文网首页
白话JS引擎运行过程

白话JS引擎运行过程

作者: 草珊瑚_6557 | 来源:发表于2019-06-06 15:17 被阅读0次

JS引擎对代码解析执行的过程,有两个阶段。
第一个阶段是构建语法树
第二个阶段是对语法树进行解析执行

第一阶段:构建语法树

构建过程按下不表,日后填坑。
若语法树无法构造,报语法错误。

第二阶段:解析执行

解析执行有三阶段:创建,执行,执行完毕。

解析执行三个阶段

创建阶段

创建阶段,创建什么?
创建执行上下文(Execution context)

执行上下文

创建执行上下文这个过程,也叫预解析(preparse).
预解析(preparse)的内容如下:

1. 创建变量对象(Variable Object)
2. 建立作用域链(Scope chain)
3. 确定this引用

1. 创建变量对象(Variable Object)

变量对象是一个对象。
变量对象的属性有函数形参(arguments)变量声明(variables)函数声明(functions)

创建变量对象的过程

示例代码1:

 function fn(a){
    console.log(a);
    var a = 123;
    console.log(a);
    
    function a(){};
    console.log(a);
    
    var b = function(){};
    console.log(b);
    
    function d(){};
 }
 
 //调用函数
 fn(1);

执行fn(1)时,对fn预解析的创建变量对象过程如下:

  1. 创建一个空对象
vo:{
// 空对象
}
  1. 形参变实参
// 找形参
vo:{
  a : undefined,
}
// 形参变实参
vo:{
  a : 1,
}
  1. 找变量声明
vo:{
  a : undefined,
  b : undefined
}
  1. 找函数声明
vo:{
    a : function a(){},
    b : undefined,
    d : function d(){}
}

2. 建立作用域链(Scope chain)

作用域链是什么?是一个数组。
数组内容是父变量对象
创建阶段作用域链就这么点内容。
举个例子:

function foo() {
    function bar() {
    }
}

foo();

创建阶段时,foo的作用域链为

foo.[[scope]] = [
  globalContext.VO
];

属性[[scope]]即foo函数的作用域链。globalContext.VO是指全局上下文的变量对象

执行foo函数。也就是bar函数创建阶段,bar的作用域链为

bar.[[scope]] = [
    fooContext.AO,
    globalContext.VO
];

而此时foo的作用域链为

foo.[[scope]] = [
  [AO],
  globalContext.VO
];

这里的[AO]是指foo函数的活动对象(Active Object)。本质就是foo函数的变量对象(Variable Object)。
同一个东西不同阶段的称呼而已。

闭包

每个函数都有作用域链,引用了父活动对象或全局变量对象。
所以,每个函数都是闭包。
因为,闭包的定义是引用了自由变量的函数。

3. 确定this指向

创建阶段的this指向undefined

执行阶段

1.修改活动对象。
2.遇到异步代码,涉及到macro-task(宏任务)micro-task(微任务)
3.赋值操作,进行内存分配。

this的变化

谁调用函数,该函数的执行上下文的this指向谁。
函数调用场景:

  • new调用
  • 对象调用
  • 系统调用

JavaScript中this的运行机制及爬坑指南

执行完毕阶段

垃圾回收策略有两个,标记清除,引用计数(已淘汰)。
标记清除策略:
(1)创建阶段对当前执行上下文的变量进行标记。
(2)执行阶段,执行到所需变量的操作时,去掉它的标记。
(3)执行完毕阶段,有标记的变量就被视为准备删除的变量。
(4)垃圾收集器销毁带标记的变量,回收它们所占用的内存空间。

引用计数被淘汰的原因是循环引用会导致垃圾回收失败。
垃圾回收策略对写代码的参考:

参考:
Google V8 的垃圾回收引擎
聊聊V8引擎的垃圾回收

参考:
https://my.oschina.net/ffwcn/blog/209465
https://juejin.im/post/5aa6693df265da23884cb571
https://www.cnblogs.com/ivehd/p/executionContext.html

相关文章

  • 白话JS引擎运行过程

    JS引擎对代码解析执行的过程,有两个阶段。第一个阶段是构建语法树。第二个阶段是对语法树进行解析执行。 第一阶段:构...

  • JavaScript 究竟是怎样执行的?

    摘要: 理解 JS 引擎运行原理。 作者:前端小智 原文:搞懂 JavaScript 引擎运行原理 Fundebu...

  • 00 NodeJs基础

    NodeJs 输入内容 运行node app.js 全局对象 引擎 js引擎电脑不识别也不理解jsjs引擎的作用就...

  • async 和 defer

    HTML加载过程 1. 两个引擎 浏览器的引擎可以分为渲染引擎和 JS 引擎。 JS 引擎相对独立,而渲染引擎又包...

  • nodejs Event Loop

    1.前置知识 node.js是一个可以运行js的平台包括fs模块、http模块以及JS引擎(v8) js引擎(单线...

  • JS引擎是如何工作的?从调用堆栈到Promise

    摘要: 理解 JS 引擎运行原理。 作者:前端小智 原文:JS引擎:它们是如何工作的?从调用堆栈到Promise,...

  • 怎么来理解Js是单线程的这句话?

    Js是单线程指的是执行Js代码的只有Js引擎主线程。Js在js引擎中同步执行,永远都是运行执行栈最顶部的代码。那么...

  • js的作用域和闭包

    当我写一段js代码并运行时,有三个非常重要的角色:引擎、 编译器、 作用域 下面模拟一段js代码运行的过程如下代码...

  • 初识 Node.js

    简介 Node.js 是基于 Chrome V8 引擎运行的一种 JavaScript 运行环境。Node.js ...

  • js 运行原理解析

    关于JavaScript 如何工作的,由以下这几个概念 JS Engline (JS引擎) Runtime(运行上...

网友评论

      本文标题:白话JS引擎运行过程

      本文链接:https://www.haomeiwen.com/subject/hwvssqtx.html