# [JavaScript] var, let 和 const 宣告變數大不同 ###### tags: `前端筆記` ## 總結 1. 不要用 `var` 了 2. `var` 切分變數的最小單位是 `Function`,所以其他在 `if` `for loop` 等「區塊作用域」用的話還是會變成「全域物件」的屬性(property)值(variableName = keyName, variableValue = value) 3. `let` 和 `const` 會有區塊作用域意即 `if` `for loop` 等等(白話來說就是不僅在 `Function` 外就掛了,在 `loop` 或 `if` 之外也會掛掉) 4. 如果會更改值就用 `let`,不會更改值就用 `const` ## 宣告方式 1. var 2. let(ES6 加入的新夥伴) 3. const(ES6 加入的新夥伴) ## var  1. 時代的眼淚,如果沒有特別的需求已經不會使用它了 2. 用 `var` 宣告的變數為全域變數(Global variables) 3. 但是在函式中用 `var` 時該變數只存活在函式中   *在 `if` 之外還有辦法讀取。* 4. 會造成提升(Hoisting)  在瀏覽器(編譯器)的眼中,函式內是長這樣子: ```javascript= var x = 100; function func (y) { var x; console.log(x); x = 150; } ``` 用 `var` 宣告變數時,要注意順序。如果在宣告以前讀取該變數,編譯器會先自動在讀取前建立該變數的名稱(但值不會帶到)。  5. 可隨意更改其值 >註解:Global variables 為「全域物件」的屬性值,在網頁中「全域物件」是 `window`,所以可以用 `window.variableName` 來讀取 / 更新值(value)。  ## let 1. 取代 `var` 的辦法 2. 宣告的變數會在「區塊內」  *`let` 宣告的變數值活在 `if` 區塊之內,但 `var` 則是會活在全域物件中* 3. 不會有提升(Hoisting)的問題  4. 可隨意更改其值 ## const 1. constant (adj.)(staying the same, or not getting less or more) 2. 宣告一個只可以讀取的常數,意即:不可更改其值 3. 像 `let` 一樣會在「區塊內」 4. 但對於「物件型別」的資料可以改變物件的值,因為常數也只是保存變數的「址參器」,只要「址參器」沒變即可  *用物件實字(Object Literal)會重新創造一個新的物件,所以就要保存新的址參器,但是 `const` 係不可改其值的,所以會報錯。* ## 考題 #### 1. 猜猜看會出現什麼?為什麼會這樣? ```javascript= var cat = "毛咪"; function f(){ console.log(cat); if(true){ var cat = "奇奇"; }; }; f(); ``` :::spoiler 答案 1. 變數最小的有效範圍為 function 2. 使用 `var` 宣告的變數會提升(hoisting),出現 *undefined* 的原因是變數已經有了,但是沒有和記憶體連結(簡單就是未賦值) ```javascript= var cat = "毛咪"; function f(){ console.log(cat); if(true){ var cat = "奇奇"; }; }; f(); // undefined // 在 JavaScript 的眼中則是 var cat = "毛咪"; function f(){ var cat; console.log(cat); if(true){ cat = "奇奇"; }; }; f(); // undefined ``` ::: #### 2. 猜猜看會出現什麼?為什麼會這樣? ```javascript= var cat = "毛咪"; function f(){ console.log(cat); if(true){ let cat = "奇奇"; }; }; f(); ``` :::spoiler 答案 1. 使用 `let` 宣告的變數不會造成提升(hoisting),所以是按照順序,跑到該行才有該變數 2. 往外找,function 內找不到的會往外層找,找到就顯示,找不到就報錯 ```javascript= var cat = "毛咪"; function f(){ console.log(cat); if(true){ let cat = "奇奇"; }; }; f(); // '毛咪' ``` ::: ## 參考資料 1. [Day.27 「var 成為時代的眼淚!」 —— ES6 區塊作用域 與 提升](https://ithelp.ithome.com.tw/articles/10273943?sc=iThomeR) 2. [語法與型別](https://developer.mozilla.org/zh-TW/docs/Web/JavaScript/Guide/Grammar_and_types) 3. [重新認識 JavaScript: Day 10 函式 Functions 的基本概念](https://ithelp.ithome.com.tw/articles/10191549)
×
Sign in
Email
Password
Forgot password
or
By clicking below, you agree to our
terms of service
.
Sign in via Facebook
Sign in via Twitter
Sign in via GitHub
Sign in via Dropbox
Sign in with Wallet
Wallet (
)
Connect another wallet
New to HackMD?
Sign up