博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
一看就懂的JS抽象语法树
阅读量:5739 次
发布时间:2019-06-18

本文共 3177 字,大约阅读时间需要 10 分钟。

前言

babel是现在几乎每个项目中必备的一个东西,但是其工作原理避不开对js的解析在生成的过程,babel有引擎babylon,早期fork了项目acron,了解这个之前我们先来看看这种引擎解析出来是什么东西。不光是babel还有webpack等都是通过javascript parser将代码转化成抽象语法树,这棵树定义了代码本身,通过操作这颗树,可以精准的定位到赋值语句、声明语句和运算语句。有兴趣的可以关注一下我的,点一个star。谢谢

什么是抽象语法树

我们可以来看一个简单的例子:

var a = 1;var b = a + 1;复制代码

我们通过这个,他是一个esprima引擎的网站,十分好用.画成流程图如下:

而他的json对象格式是这样的:

{    "type": "Program",    "body": [        {            "type": "VariableDeclaration",            "declarations": [                {                    "type": "VariableDeclarator",                    "id": {                        "type": "Identifier",                        "name": "a"                    },                    "init": {                        "type": "Literal",                        "value": 1,                        "raw": "1"                    }                }            ],            "kind": "var"        },        {            "type": "VariableDeclaration",            "declarations": [                {                    "type": "VariableDeclarator",                    "id": {                        "type": "Identifier",                        "name": "b"                    },                    "init": {                        "type": "BinaryExpression",                        "operator": "+",                        "left": {                            "type": "Identifier",                            "name": "a"                        },                        "right": {                            "type": "Literal",                            "value": 1,                            "raw": "1"                        }                    }                }            ],            "kind": "var"        }    ],    "sourceType": "script"}复制代码

众多的引擎

chrome有v8,firefix有spidermonkey.还有一些常用的引擎有:

  • esprima
  • acron
  • Traceur
  • UglifyJS2
  • shift

下面是一些引擎的速度对比,以及用不同的框架,引擎们的加载速度:

我个人认为,封装的越完美的,其实解析的时间更长,引擎之间也是acron这个速度比较优秀,babel引擎前身就是fork这个项目的。

AST的三板斧

  • 通过esprima生成AST
  • 通过estraverse遍历和更新AST
  • 通过escodegen将AST重新生成源码

我们可以来做一个简单的例子:

1.先新建一个test的工程目录 2.在test工程下安装esprima、estraverse、escodegen的npm模块

npm i esprima estraverse escodegen --save复制代码

3.在目录下面新建一个test.js文件,载入以下代码:

const esprima = require('esprima');let code = 'const a = 1';const ast = esprima.parseScript(code);console.log(ast);复制代码

你将会看到输出结果:

Script {  type: 'Program',  body:   [ VariableDeclaration {       type: 'VariableDeclaration',       declarations: [Array],       kind: 'const' } ],  sourceType: 'script' }复制代码

4.再在test文件中,载入以下代码:

const estraverse = require('estraverse');estraverse.traverse(ast, {    enter: function (node) {        node.kind = "var";    }});console.log(ast);复制代码

输出的结果:

Script {  type: 'Program',  body:   [ VariableDeclaration {       type: 'VariableDeclaration',       declarations: [Array],       kind: 'var' } ],  sourceType: 'script' }复制代码

5.最后在test文件中,加入以下代码:

const escodegen = require("escodegen");const transformCode = escodegen.generate(ast)console.log(transformCode);复制代码

输出的结果:

var a = 1;复制代码
  • 通过这三板斧:我们将const a = 1转化成了var a = 1

有没有babel的感觉0.0

推荐网站

总结

抽象树在前端用的很多很多,现在流行的工具,不管是webpack还是babel都会通过那个三板斧的流程,这里我只是大致介绍一下,过段时间,会出一篇抽象树的语法,有兴趣的也可以把esprima的源码看一下,为什么是esprima呢,因为esprima的资料比较多,而acron比较轻量级。有兴趣的可以关注一下我的,记得点个star,就当是对笔者的支持,谢谢。

转载地址:http://dvfzx.baihongyu.com/

你可能感兴趣的文章
针对web服务器容灾自动切换方案
查看>>
LTE学习笔记(一)——背景知识
查看>>
突破媒体转码效率壁垒 阿里云首推倍速转码
查看>>
容器存储中那些潜在的挑战和机遇
查看>>
程序员该懂一点儿KPI
查看>>
R语言的三种聚类方法
查看>>
55%受访企业将物联网战略视为有效竞争手段
查看>>
深入理解Python中的ThreadLocal变量(上)
查看>>
如果一切即服务,为什么需要数据中心?
查看>>
《游戏开发物理学(第2版)》一导读
查看>>
Erlang简史(翻译)
查看>>
深入实践Spring Boot2.4.2 节点和关系实体建模
查看>>
信息可视化的经典案例:伦敦地铁线路图
查看>>
10个巨大的科学难题需要大数据解决方案
查看>>
Setting Up a Kerberos server (with Debian/Ubuntu)
查看>>
Node.js Undocumented(1)
查看>>
用 ThreadLocal 管理用户session
查看>>
setprecision后是要四舍五入吗?
查看>>
shiro初步 shiro授权
查看>>
上云就是这么简单——阿里云10分钟快速入门
查看>>