輕鬆學習 JavaScript(5):簡化函式提升

發表於2017-11-21

為了理解函式提升,讓我們從以下程式碼開啟我們的學習之旅:

應該輸出什麼呢?

在任何其他程式語言中,這裡的輸出將會是reference error。但是,在JavaScript中,你將得到undefined作為輸出。為什麼?因為JavaScript會提升變數到執行上下文的頂部。執行上下文可以是宣告變數的函式,也可以是宣告變數的JavaScript檔案。所以,讓我們用函式重寫上面的程式碼片段:

這裡,變數“foo”提升到函式abc執行上下文的頂部;這意味著你可以在宣告之前訪問foo。簡而言之,無論何時你宣告一個變數,JavaScript直譯器都可以將其分成兩個語句:

  • 宣告一個變數。
  • 賦值。

變數的宣告位於執行上下文的頂部,而賦值發生在建立變數的位置。所以上面的程式碼片段被分解成兩個語句,如下圖所示:Hoisting-1

 

變數foo被提升到函式abc的執行上下文的頂部,因此當你在宣告之前使用它時,你會得到“undefined”作為輸出。

請記住,使用let語句宣告的變數不會被提升到執行上下文的頂部。

現在你知道JavaScript中的變數是如何被提升的了,接下來讓我們來探討JavaScript中的函式提升。在JavaScript中,可以通過兩種方式來建立函式:

  • 作為宣告而建立的函式。
  • 作為表示式而建立的函式。

作為宣告或語句建立的函式作為一個整體提升到執行上下文的頂部。但是,作為表示式建立的函式會像變數一樣提升。

為了說明這一點,讓我們建立一個作為語句的函式:

在上面的程式碼中,如果你在函式建立之前使用函式,那麼你會得到hello的輸出。發生這種情況的原因是,作為語句建立的函式會當作一個整體被提升到執行上下文的頂部。

無論何時建立作為語句的函式,都可以在函式建立之前使用該函式。因此,如果你在第5行建立作為語句的函式,那麼你可以在第1-4行中使用該函式,因為函式語句會隨函式主體一起提升到執行上下文的頂部。

函式語句會隨函式主體一起提升到執行上下文的頂部。

函式表示式會像一個變數一樣被提升到執行上下文的頂部。請看下面的程式碼:

你正在程式碼中建立函式foo作為表示式,所以JavaScript會像普通變數一樣提升它。 JavaScript會像下圖所示那樣處理上面的程式碼:

Hoisting-2

正如你在上面的圖片中看到的那樣,foo在執行上下文的頂部被宣告為一個變數,然而,在變數foo中的函式賦值發生在第6行,也就是建立作為表示式函式的地方。所以,當你嘗試執行上面的程式碼時,你會得到錯誤undefined is not a function,如下圖所示:

Hoisting-3

因此,你不能在函式表示式被建立之前使用函式表示式,因為只有函式宣告會提升到頂部。

綜上所述:

  • 函式語句隨函式主體一起被提升到執行上下文的頂部。你可以在函式建立之前使用作為語句建立的函式。
  • 函式表示式在建立之前不能使用。只有宣告部分會被提升,賦值發生在建立函式的那一行。

在“輕鬆學習JavaScript”系列的下一篇文章中,我們將介紹JavaScript中更為重要的概念,敬請期待。

相關文章