JavaScript 全攻略:克服 JS 的奇怪部分筆記 - 第二章
範圍鍊(scope chain)
前言:
在瞭解了上一篇-執行堆(Execution stack)、執行環境(Execution environment)與變數環境(Variable environment)之後,接下來要講的範圍鍊(scope chain)並不會顯得太生疏。
先看一範例程式碼:
這裡運用上一章提到的觀念先來看看:
(1).一開始全域等級,創造Global Execution context,在這個環境中有個myVar此時的值是1
(2).接著call a(),創造了一個execution context,myVar宣告為2,放入Execution stack中
(3).在function a 中call 了 b,又創造了一個execution context
但此時b的execution context的myVar未設定,那他的值是多少?
這邊有一個觀念,就是JavaScript中的Execution context建立的時候,都會各自去參照一個外部環境(outer environment),js在處理變數的時候,先去看自己當下環境的變數,若是沒有這個變數,就會去外部環境搜索,那要怎麼判斷外部環境在哪?很簡單,只要看看程式碼是寫在哪就可以了,以function b來說,他是寫在Global的等級下,所以b的外部環境會參照到Global,a也是同樣的道理。
如下圖所示:
而這一連串參造會形成一條鍊,最後鍊結到Global Execution context,我們稱為範圍鍊(Scope chain)
範圍鍊(Scope Chain):
如剛剛的範例所示,為了找myVar而從內層找到最外層(global)的這條鍊,就稱之。
再看一個例子:
我們此時把function b 放置function a之中,這個時候再來看看myVar是多少,來看看這條scope chain長甚麼樣子。
(1).一開始全域等級,創造Global Execution context,在這個環境中有個myVar此時的值是1
(2).接著call a(),創造了一個execution context,放入Execution stack中
(3).最後,在function a 中call 了 b,又創造了一個execution context
現在我們就來對照外部環境,畫出scope chain
(1).function b 是在 function a 的環境中,故b的外部環境是a
(2).function a 是在 global 的環境中,故a的外部環境是Global Execution Context,我們就可以畫出如下的scope chain
最後,那console.log(myVar)是多少?
從Execution stack的最上層開始看,一開始b參考a,但a中也沒有myVar,故再參考到最外層的Global的myVar
所以console.log(myVar)印出是1