提升
js引擎和编译器
变量和函数如何提升 ,js代码的编译阶段;
js有个比较经典的问题,如:
a = 10;
console.log(a);
var a;
或者
a = 10;
var a;
console.log(a);
你觉得他会输出什么呢?undefined?ReferenceError? 不不不,他会显示10!为什么呢待会说。再看下一个例子。
console.log(a);
var a = 10;
这个又会展示什么呢?10?还是ReferenceError?但其实这是会展示undefined!
这里说一下undefined和ReferenceError的区别,undefined是表示这个变量声明了但是还没有任何值,只是已经在作用域里开辟了一块地方来存放,而ReferenceError表示的是这个变量声明,作用域里面没有任何东西。
因为js的代码在执行之前会有编译器进行编译一次,这次会把所有的变量声明和函数声明提前执行比如var a = 10;
语句,在你看来这只是一个语句,而在系统看来是分为两个的var a ; 和a=10;
而前者是提前执行的,所以这就叫提升。并且js的提升在每个作用域里都是有效的,不光是全局环境下。
思考:
foo();
function foo () {
console.log(a);// undefined;
var a;
a = 10;
}
在这段代码里的foo函数会提前声明,所以foo();可以正常的执行。但是var会提前在输出之前执行,所以会显示undefined;
也就是说整个代码会呈现下面的形式:
function () {
var a;
console.log(a);
a = 10;
}
foo();
还有一个是函数的优先性,函数声明优先于变量的声明,如:
foo();//2
var foo;
foo = function () {
console.log(1);
}
function foo () {
console.log(2)
};