1.JavaScript是一门高级的编程语言
- 机器语言:100010001000,一些机器指令;
- 汇编语言:mov ax bx,一些汇编指令;
- 高级语言:C、C++、Java、JavaScript、Python; 最终运行都是要转换成机器语言来运行的。
2. 浏览器的工作原理
3.浏览器的内核
- Gecko: 早期网景浏览器和火狐浏览器内核
- Trident:微软IE浏览器,现在已经转向新的Edge浏览器(Blink内核)
- Webkit:苹果safari浏览器内核
- Blink:谷歌Chrome浏览器内核
4.浏览器渲染过程
- 浏览器首先解析html文件时,按自上而下的顺序解析,如果过程中遇到了JavaScript标签,则会停止解析,浏览器会将控制权给到js引擎,js引擎去加载和执行js代码
- 通过解析html标签和js代码得到对应的DOM树,与Css的样式规则相结合形成渲染树(Render Tree)
- 渲染树的每个元素包含的内容都是计算过的,它被称之为布局layout。浏览器使用一种流式处理的方法,只需要一次pass绘制操作就可以布局所有的元素。
- 将渲染树的各个节点绘制到屏幕上,这一步被称为绘制painting.
- 最终展示页面
5. V8引擎的执行原理
V8引擎是目前比较强大的JS引擎,由C++编写,可以独立运行,也可以嵌入到任何C++应用中。
- parse模块:语法解析和词法解析,将JS源码转化为AST抽象语法树,转换的AST语法树有点类似JSON格式。astexplorer.net/ 在线解析网址如图:
babel的实现原理就类似于这种,先将ES6语法转为抽象语法树,再将抽象语法树,转为ES5。
- lgnition:是一个解释器,它会将AST抽象语法树,转成字节码。同时会帮助TurboFan模块收集所需要的信息(比如函数参数的类型信息)
- TurboFan:是一个编译器:它会将字节码编译成机器码。如果一个函数多次调用,就被被它标记成热点函数,并被TurboFan转换成优化的机器码,提高机器执行性能。但是如果后续执行中函数的参数类型变化了,会逆向优化成字节码
6. 初始化全局对象
js引擎在执行代码前,会在堆内存中创建一个全局对象:Golbal Objcet(GO)
- 该对象所有的作用域都可以访问到
- 里面会包含一些内置的方法Date、String、setTimeout等等
- 也包含一个window属性指向自己
7. 执行上下文栈
- js引擎内部有一个执行上下文栈(Execution Context Stack 简称ECS),是用于执行代码的调用栈
- 执行的是全局的代码块
- 全局的代码块为了执行会创建一个 Global Execution Context (GEC)
- GEC会被放到ECS中去执行
- GEC被放到ECS中包含两部分内容
- 第一部分:在代码执行前,在parser转成AST的过程中,会将全局定义的变量、函数等加到GO中,但是并不会赋值。这个过程也被称作变量提升
- 第二部分:在代码执行中,对变量赋值,或者执行其他函数
8. 函数执行上下文
- 执行上下文栈在遇到函数的时候,就会根据函数体创建一个函数执行上下文(Functional Execution Context 简称FEC),并且压入到ECS中
- FEC中包含三部分
- 第一部分: 在解析函数成为AST树结构时,会创建一个Activation Object(AO)。AO中包含形参、arguments、函数定义和指向函数的对象,定义的变量
- 第二部分: 作用域链:由VO(在函数中就是AO)和父级AO组成,查找时会一层层查找。
- 第三部分: this绑定的值