JavaScript 详解预编译原理


Posted in Javascript onJanuary 22, 2017

JavaScript 预编译原理

今天用了大量时间复习了作用域、预编译等等知识

看了很多博文,翻开了以前看过的书(好像好多书都不会讲预编译)

发现当初觉得自己学的很明白,其实还是存在一些思维误区 (很多博文具有误导性)

今晚就整理了一下凌乱的思路

先整理一下预编译的知识吧,日后有时间再把作用域详细讲解一下

大家要明白,这个预编译和传统的编译是不一样的(可以理解js预编译为特殊的编译过程)

JavaScript是解释型语言,

既然是解释型语言,就是编译一行,执行一行

传统的编译会经历很多步骤,分词、解析、代码生成什么的

日后有时间再给大家科普

下面就给大家分享一下我所理解的JS预编译

JavaScript运行三部曲

脚本执行js引擎都做了什么呢?

  • 语法分析
  • 预编译
  • 解释执行

在执行代码前,还有两个步骤

语法分析很简单,就是引擎检查你的代码有没有什么低级的语法错误

解释执行顾名思义便是执行代码了

预编译简单理解就是在内存中开辟一些空间,存放一些变量与函数

理解了预编译对大家理解作用域同样有帮助

JS预编译什么时候发生

我当初思维误区也发生在这里

预编译到底什么时候发生

希望大家不要让上面的运行过程让你产生误会,

误以为预编译仅仅发生在script内代码块执行前

这倒并没有错

预编译确确实实在script代码内执行前发生了

但是它大部分会发生在函数执行前

JS预编译实例

举例前,先来思考一下这几个概念:

  • 变量声明 var…
  • 函数声明 function…
<script>
  var a = 1;// 变量声明
  function b(y){//函数声明
    var x = 1;
    console.log('so easy');
  };
  var c = function(){//是变量声明而不是函数声明!!
    //...
  }
  b(100);
</script>
<script>
  var d = 0;
</script>

让我们看看引擎对这段代码做了什么吧

1.页面产生便创建了GO全局对象(Global Object)(也就是大家熟悉的window对象)

2.第一个脚本文件加载

3.脚本加载完毕后,分析语法是否合法

4.开始预编译

查找变量声明,作为GO属性,值赋予undefined
查找函数声明,作为GO属性,值赋予函数体

//伪代码
GO/window = {
  //页面加载创建GO同时,创建了document、navigator、screen等等属性,此处省略
  a: undefined,
  c: undefined,
  b: function(y){
    var x = 1;
    console.log('so easy');
  }
}

解释执行代码(直到执行函数b)

//伪代码
GO/window = {
  //变量随着执行流得到初始化
  a: 1,
  c: function(){
    //...
  },
  b: function(y){
    var x = 1;
    console.log('so easy');
  }
}

执行函数b之前,发生预编译

  • 创建AO活动对象(Active Object)
  • 查找形参和变量声明,值赋予undefined
  • 实参值赋给形参
  • 查找函数声明,值赋予函数体
//伪代码
AO = {
  //创建AO同时,创建了arguments等等属性,此处省略
  y: 100,
  x: undefined
}

解释执行函数中代码

第一个脚本文件执行完毕,加载第二个脚本文件

第二个脚本文件加载完毕后,进行语法分析

语法分析完毕,开始预编译

重复最开始的预编译步骤……

大家要注意,

预编译阶段发生变量声明和函数声明,没有初始化行为(赋值),匿名函数不参与预编译

只有在解释执行阶段才会进行变量初始化

嗯~最后收一下尾

总结

预编译(函数执行前)※

1. 创建AO对象(Active Object)
2. 查找函数形参及函数内变量声明,形参名及变量名作为AO对象的属性,值为undefined
3. 实参形参相统一,实参值赋给形参
4. 查找函数声明,函数名作为AO对象的属性,值为函数引用

预编译(脚本代码块script执行前)

1. 查找全局变量声明(包括隐式全局变量声明,省略var声明),变量名作全局对象的属性,值为undefined
3. 查找函数声明,函数名作为全局对象的属性,值为函数引用

理解了预编译对理解提升行为,this指向,作用域及性能等问题都有很大帮助

感谢阅读,希望能帮助到大家,谢谢大家对本站的支持!

Javascript 相关文章推荐
javascript 隐藏/显示指定的区域附HTML元素【legend】用法
Mar 05 Javascript
js 蒙版进度条(结合图片)
Mar 10 Javascript
一个简单的jQuery插件制作 学习过程及实例
Apr 25 Javascript
在iframe里的页面编写js,实现在父窗口上创建动画效果展开和收缩的div(不变动iframe父窗口代码)
Dec 20 Javascript
浅谈Javascript线程及定时机制
Jul 02 Javascript
jquery自定义表格样式
Nov 23 Javascript
Node.js读写文件之批量替换图片的实现方法
Sep 07 Javascript
Vue.js学习记录之在元素与template中使用v-if指令实例
Jun 27 Javascript
vuex与组件联合使用的方法
May 10 Javascript
微信小程序学习笔记之获取位置信息操作图文详解
Mar 29 Javascript
JavaScript 函数用法详解【函数定义、参数、绑定、作用域、闭包等】
May 12 Javascript
基于JavaScript实现年月日三级联动
Jun 22 Javascript
JavaScript中匿名函数的递归调用
Jan 22 #Javascript
Javascript中字符串和数字的操作方法整理
Jan 22 #Javascript
loading动画特效小结
Jan 22 #Javascript
全面总结Javascript对数组对象的各种操作
Jan 22 #Javascript
通过jsonp获取json数据实现AJAX跨域请求
Jan 22 #Javascript
JS实现点击表头表格自动排序(含数字、字符串、日期)
Jan 22 #Javascript
node.js基于mongodb的搜索分页示例
Jan 22 #Javascript
You might like
上海永华YH-R296(华普R-96)12波段立体声收音机的分析和打理
2021/03/02 无线电
PHP弹出提示框并跳转到新页面即重定向到新页面
2014/01/24 PHP
PHP中date与gmdate的区别及默认时区设置
2014/05/12 PHP
php根据用户名和手机号查询是否存在手机号码
2017/02/16 PHP
PHP SPL 被遗落的宝石【SPL应用浅析】
2018/04/20 PHP
JS宝典学习笔记(下)
2007/01/10 Javascript
用javascript实现的仿Flash广告图片轮换效果
2007/04/24 Javascript
基于JQuery.timer插件实现一个计时器
2010/04/25 Javascript
javascript获取作用在元素上面的样式属性代码
2012/09/20 Javascript
Web表单提交之disabled问题js解决方法
2015/01/13 Javascript
jQuery根据用户电脑是mac还是pc加载对应样式的方法
2015/06/26 Javascript
谈谈JavaScript类型系统之Math
2016/01/06 Javascript
JS+CSS实现DIV层的展开、收缩效果
2016/01/28 Javascript
Sequelize中用group by进行分组聚合查询
2016/12/12 Javascript
详解Vue2.X的路由管理记录之 钩子函数(切割流水线)
2017/05/02 Javascript
详解如何使用webpack打包Vue工程
2017/05/27 Javascript
canvas+gif.js打造自己的数字雨头像的示例代码
2017/10/26 Javascript
vue结合element-ui使用示例
2019/01/24 Javascript
jQuery事件blur()方法的使用实例讲解
2019/03/30 jQuery
关于layui 弹出层一闪而过就消失的解决方法
2019/09/09 Javascript
vue data恢复初始化数据的实现方法
2019/10/31 Javascript
[05:02][DOTA2]DOTA进化论 第一期
2013/09/27 DOTA
pycharm 使用心得(五)断点调试
2014/06/06 Python
Python基于scapy实现修改IP发送请求的方法示例
2017/07/08 Python
python pycharm的安装及其使用
2019/10/11 Python
python Popen 获取输出,等待运行完成示例
2019/12/30 Python
Html5嵌入钉钉的实现示例
2020/06/04 HTML / CSS
李宁官方网店:中国运动品牌
2017/11/02 全球购物
捷克移动配件网上商店:ProMobily.cz
2019/03/15 全球购物
乡镇综治宣传月活动总结
2014/07/02 职场文书
助人为乐道德模范事迹材料
2014/08/16 职场文书
保密工作整改报告
2014/11/06 职场文书
文艺节目主持词
2015/07/06 职场文书
2017元旦、春节期间廉洁自律承诺书
2016/03/25 职场文书
Python进行区间取值案例讲解
2021/08/02 Python
oracle删除超过N天数据脚本的方法
2022/02/28 Oracle