现象
1. 如下代码,将会输出什么呢?
var n = 1;
function test () {
console.log('log1 :' + n);
var n = 2;
console.log('log2 :' + n);
}
test ();
console.log('log3 :' + n);
2. 输出如下:
log1 :undefined
log2 :2
log3 :1
3. 解释:
var n = 1; //全局变量
function test () {
//var n; //1.变量声明(变量提升至函数内首行),覆盖全局变量声明
console.log('log1 :' + n); //2.n现只声明,未赋值
var n = 2; //3.函数作用域内局部变量赋值
console.log('log2 :' + n); //4.调用n值输出
}
test (); //执行函数
console.log('log3 :' + n); //5.全局作用域下输出n
4.函数提升
(function () {
// var fn1,function fn2 () {};//隐式声明fn2(),只声明fn1变量
fn2();
fn1();
var fn1 = function () {};
function fn2 () {};
}) ()
在Google控制台中运行此立即调用代码时出错信息为>Uncaught TypeError: fn1 is not a function,这说明函数表达式只将变量fn1提升函数提升失败,而形如函数声明fn2已在开头隐式声明函数提升成功。
** 说明**
1.变量如果不在全局作用域声明那么就在函数作用域声明,变量使用表达式赋值定义时也是先声明,调用时才赋值。
2.在函数作用域内变量分为执行前、执行时、执行后,执行前声明变量,执行时调用变量,执行后若无其他调用则回收。
应用
了解上述内容之后,编码时需要避免变量提升这类情况。具体是编码规范化,优先在作用域内首行声明变量,且只在一处使用必须的关键字var声明变量,形如:
(function () {
var a,
b,
c;
//其他代码
} ) ()