Posted in 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。

 

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s