要理解javascript的变量声明和函数提升,重要的是理解浏览器对javascript代码的处理过程。
包括变量和函数在内的声明都会在代码被执行时被先处理。
例子:
在编辑器中写:var a = 1;
浏览器处理过程是:(先声明变量)var a;(再变量赋值)a = 1;
1.变量的提升:
例子:
function test(){
a = 2;
var a;
console.log(a) //2
}
实际浏览器处理过程:
function test(){
var a;
a = 2;
console.log(a) //2
}
例子2:
function test(){
console.log(a)
a = 2;
var a ;
}
实际浏览器处理过程:
function(){
var a;
console.log(a) //undefined 因为a还没有被赋值
a = 2;
}
2.函数声明提升:
函数声明的提升优先大于变量的提升,同样这样的声明的时候,不论先后顺序,函数的声明都会覆盖变量的声明
例子1:
var a = 1;
function f(){
console.log(a);
var a = 2;
console.log(a);
} f();
实际浏览器处理过程:
var a;
a = 1;
function f(){
var a ;
console.log(a)
//由于a在第一个console.log(a)语句之前就已经定义了,但是并没有赋值,因此此时a的指是undefined
a = 2;
console.log(a)
// 第二个console.log(a)语句之前,a已经完成赋值为2,所以输出的结果是2
}
例子2:
函数声明语法:
f("hello");
function f(a){
console.log(a)//hello
}
函数表达语法:
f("hello");
var f = function (a){
console.log(a)//会报错。f is not function
}
为什么会报错,理解下浏览器处理过程:
var f;
f("hello");//报错,f虽然被定义了,但是没有被赋值所以会出现f is not function,如果把它放在最后就能执行成功
f = function (a){
console.log(a)
}
例子3:
getName();
var getName = function(){
console.log("小明");
}
function getName(){
console.log("大明");
}
getName();
我们来解析一下例子3浏览器是如何处理的:
var getName;//首先变量被提升到顶部,定义未被赋值
function getName(){//函数声明也被被提升到顶部
console.log("大明")
}
getName();//调用函数声明,打印“大明”
getName = function() {//变量赋值
console.log("小明")
}
getName() //调用函数,顶部的函数声明又被函数表达式的赋值操作给覆盖了,所以输出小明。
如有错误请指正,省得误人子弟