这篇文章是我做web前端开发讲师的时候写的一篇文章,如有部分雷同,纯属巧合。这里放在头条上分享给各位朋友,主要希望是给热爱前端编程的初学者一些小小的帮助,了解解析JS的编译原理,如果你是前端大牛,也欢迎在评论区留言发表自己的观点,谢谢!
1. 编译原理
1.1. 代码分析:先来了解一个奇怪的现象
你可以打开开发工具尝试一下
大家预期的结果是什么 ,1,1,2 ? No,No,No!!
要想知道为什么,我们就得来了解下JavaScript引擎的执行原理。
1.2. JavaScript引擎执行原理(了解)
首先,在代码领域中,代码引擎是用来读懂开发者编写代码的一段程序。就如我们编写了一段的JavaScript代码(var a = 1 +1),JavaScript引擎就是用来看懂(解析)这段JavaScript代码,计算获得结果2,并将a的值变为2。
User.java ==> User.class(在java中,需要将用户写的.java的文件编译成.class文件)
User.js ==>User.js(在JavaScript,确实这样的,为什么?)
这里需要了解一下,编程语言主要分为两大类:编译型语言和解释型语言。对于静态语言来说(如Java、C++、C),处理上述这些事情的叫编译器(Compiler),相应地对于JavaScript这样的动态语言则叫解释器(Interpreter)。这两者的区别用一句话来概括就是:编译器是将源代码编译为另外一种代码(比如机器码,或者字节码),而解释器是直接解析并将代码运行结果输出。我们常用的firebug就是一个JavaScript解释器
当JavaScript引擎解析脚本时,分为“预编译”和“解释执行”两个阶段。
1、“预编译”阶段。首先会创建一个环境的上下文对象,然后把使用var声明的变量,作为上下文对象的属性,以undefined先行初始化;使用function关键字声明的函数,也作为上下文对象的属性,定义出来,而函数则保留了定义的内容。----在这个过程中,函数定义的优先级 高于 变量 定义。
2、“解释执行”阶段。遇到变量解析,会先在当前上下文对象中找,如果没找到并且当前上下文对象有prototype属性,则去原型链中找,否则将会去作用域链中找。
结合实际案例,请大家分析如下代码的执行结果:
案例一:
// 正确
alert(num1); // 返回值undefined
var num1 =100;
alert(num1); // 返回值100
案例二:
// 正确
fn(); // 调用函数,返回值 ==> 函数调用成功!!
function fn(){
alert(‘函数调用成功!!’);
}
案例三:
// 错误
var func = "this is a variable"
function func(){
alert("hello!")
}
func(); // ==> func is not a function
案例四:
// 错误
fn(); // 调用失败,TypeError: fn is not a function
var fn = function(){
alert('函数调用成功!!');
};
总结:每个代码块都是一个独立的解析空间。
分块后,前一块的内容先执行,后一块的内容后执行。就不会出现不按原计划执行代码的情况了。
关于JS的编译原理,我的理解就是以上,结合相应的实例进行分析,如果您有你的观点或想法欢迎请在评论区留言,谢谢!