1、什么是预解释?
在当前作用域下,JS代码执行之前,首先会把带var/function关键字的进行提前的声明(declare)或者定义(defined)。
2、预解释是如何操作的?
a.带var关键字的在预解释阶段只完成了提前的声明;b.带function关键字的在预解释阶段完成了声明和定义两个操作。
3、预解释的注意点?
a.不管条件判断是否成立,判断体中的内容都要进行预解释;
例如:if (!(‘a‘ in window)) {
var a=12;
//判断‘a‘是否为window的一个属性名,因为预解释的时候声明了‘a‘,所以为true,取反为false,条件不成立,a=12执行不了,输出a=undefined;
}
b.预解释的时候只对"="等号左边的变量进行预解释,右边代表的都是值,是不进行预解释的;
例1:fn(); //可以在函数前面执行,因为在预解释的时候,fn声明和定义都完成了
function fn(){
console.log(‘ok‘);
}
例2:fn(); //这样就会报错fn is not a function,因为在预解释的时候只是对等号左边的值进行了预解释,此时fn的值是undefined,不是一个函数,不能执行
var fn=function(){
console.log(‘ok‘);
}
3、在全局作用域下预解释的时候,自执行函数中的function是不参与的,当代吗执行到对应的区域后,声明、定义、执行一起完成;
4、虽然函数体中return下面的代码是不执行的,但是需要进行私有作用域下的预解释,而return后面的是返回值,是不进行预解释的;
例如:var a=1;
function fn(){
console.log(a); //私有作用域下的预解释,首先在私有作用域中var a,说明a是私有变量,但是return下面的代码不执行,所以a为undefined;
return function(){ }; // return后面的不进行预解释,返回的是这个函数对应的地址;
var a=10;
}
fn();
5、在预解释的时候,如果发现名字冲突了,不需要重新声明,但是需要重新的赋值。(在JS中不管是变量还是函数,只要名字一样了,就是相互冲突,JS中一个名字就代表一个变量,只不过存储的值可以是任意数据类型的)
在全局作用域下不管是声明变量还是定义函数,都是在给window增加属性名。
例如:fn(); //输出结果2
function fn(){ console.log(1); }
fn(); //输出结果2
var fn=13;
fn(); //报错
function fn(){ console.log(2); }
fn(); //输出结果2