發表於 Javascript 筆記

Javascript – variable scope

2018-05-18 補充,參考這位印度人的講解,超級厲害,把scope觀念講得超明寮,雖然英文很有雷。Youtube系列影音

http://javascriptissexy.com/javascript-variable-scope-and-hoisting-explained/

http://www.w3schools.com/js/js_hoisting.asp

Javascript的變數範疇又差點破壞我對PHP變數的理解 (= =)

global vs local:跟PHP一樣的是local變數僅能運作在local範圍,global範圍是不能存取。好詭異的差異在,居然在local範疇(函數)可以存取到global變數。

  1. local變數:函數(function)裡面,使用var定義的為local,不是用var定義的變數表示來自global。
  2. global變數:函數以外使用var定義,或者不須用var定義。
var a = 100;  //global
b = 1000;  //global
function foo() {
    var c;  //local
    a++;  //來自global的a
}

console.log(foo());  //101
console.log(foo());  //102

 

2018-05-18 印度人補充:javascript雖然是直譯式語言,但它其實還是有分兩個階段執行,Compilation 與 Interpretation


var a = 10;

function myFn() {

var b = 10;

var c = b;

console.log(a + b);

}

myFn();

compilatation階段,只是註冊變數(包含函數),把它歸到正確的scope。所以上面的code總共有四個變數要註冊。var a 與 myFn 註冊成global變數、var b 與 var c 註冊成 myFn scope 的變數。指派值與console.log() 與 myFn() 在這個階段會被跳過。

interpretation階段,開始指派值與執行。a = 10,在global找到了a變數,所以把10指派給a; 接著的function myFn()會被跳過,因為它不是執行。而是最後一行的myFn()才去執行。b = 10 在myFn scope找到b變數,所以把10指派給b、c = b 在myFn scope找到c變數也找到b變數,把找到的b值指派給c。最後把console.log()執行。

 

hoisting(提升):JS引擎運作時會自動把宣告(定義)的變數拉提到該範疇的最上方,初始化變數不算是宣告喔,用例子看比較清楚。

//global範疇
x = 5;
console.log(x);  //5
var x; //定義變數x, 會被提升至第1行(x=5)之前

//先宣告再給值(等同上方code)
var x;
x = 5;

//local範疇
var name = 'nicole';
function getName() {
    //依據第一段定義,它應該是global的name(nicole)。
    //但是因為底下有var name,會被移置到函數內容第一行,所以它是local變數。
    console.log(name);  //undefined
    var name;
    name = 'Amuro';
}
getName();

//合成底下兩行變一行也是undefined
//因為JS引擎只會提升宣告,初始化值並不會被提升。
var name;
name = 'Amuro';
var name = 'Amuro';

所以養成在各個範疇就宣告(定義)變數的好習慣,才不容易造成bug。

 

廣告

發表迴響

在下方填入你的資料或按右方圖示以社群網站登入:

WordPress.com 標誌

您的留言將使用 WordPress.com 帳號。 登出 /  變更 )

Google+ photo

您的留言將使用 Google+ 帳號。 登出 /  變更 )

Twitter picture

您的留言將使用 Twitter 帳號。 登出 /  變更 )

Facebook照片

您的留言將使用 Facebook 帳號。 登出 /  變更 )

連結到 %s