歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
Linux教程網 >> Linux編程 >> Linux編程 >> JavaScript變量提升(Hoisting)

JavaScript變量提升(Hoisting)

日期:2017/3/1 9:07:21   编辑:Linux編程

定義:函數聲明和變量聲明總是被JavaScript解釋器隱式地提升(hoist)到包含他們的作用域的最頂端。

注意這裡說的是變量或函數的'聲明'會被提升到其作用域頂端
另一個需要注意的是作用域。我們知道Javascript中的作用域只有兩種,一種是全局作用域,一種是函數作用域(局部作用域) 。是沒有塊級作用域等概念的。

下面我們根據這個定義來解釋解釋變量提升這個特性

首先來一段代碼

var x = 'good';
(function () {
   console.log(x);
})();

看一下控制台的輸出結果:

good

這一點應該都沒問題吧!聲明一個變量 x 並初始化,然後在匿名函數創建的局部作用域中輸出這個 x。

那如果這樣呢:

var x = 'good';
(function () {
   console.log(x);
   var x = 10; // 在這裡添加一行對x的定義
})();

發現結果為:

undefined

我們腦補一下過程會覺著這段代碼應該如同之前那段代碼一樣,在console.log的時候輸出原有的 x 的值,而又在其下方重新定義一遍 x 才對,那麼輸出結果也應該和之前一樣才對。為什麼不一樣呢!

這個時候就是變量提升在起作用了,變量提升的定義裡說到變量的聲明會被提升到其作用域最前端。
那就是說我們在這段代碼最後一行的var x = 10 被隱式的做出了調整,var x實際上被提升到了這段代碼所在作用域(也就是這個匿名函數定義的作用域)的最前面,那就相當於這樣一段代碼:

var x = 'good';
(function () {
   var x; // 變量聲明被隱式提升
   console.log(x);
   x = 10; 
})();

如果是這樣一段代碼的話,那就很好解釋了,其 x 在匿名函數定義的作用域中聲明以後覆蓋了全局作用域中的 x ,而這個 x 在這樣一段代碼裡僅僅是聲明有這個 x ,還沒賦值,就被 console.log 掉了,自然輸出結果是 undefined 咯。
那對於函數提升呢!我們可以用這樣一段代碼來理解:

func();

function func() {
    console.log('nice');
}

輸出結果:

nice

這段代碼中呢函數的調用時在函數的定義之前。如果按照javascript的規矩,其代碼是按其先後順序一行一行的執行的話,那麼在 func() 做出函數調用的動作的時候,其前面是沒有任何關於func 這一函數的定義的。
這裡之所以能正確調用這個 func 函數,也是由於在整個javascript代碼執行前,其中的函數聲明被提升到了其作用域的最前面,這樣的話在調用func() 函數的時候自然能正確執行而不會出錯。

那以後遇到這樣的代碼 :

(function() {
    var x = 10;
    var y = 'haha';
    var z = 13.6;
})()

那不就是相當於是

(function() {
    var x, y, z; // javascript的變量提升機制
    x = 10;
    y = 'haha';
    z = 13.6;
})()

這個特性在書寫javaScript代碼的時候需要多多注意,最好將變量聲明一類的東西就直接寫在其作用域的最開頭,這樣就不會引發一些不必要的錯誤。

Copyright © Linux教程網 All Rights Reserved