【JavaScript 筆記】語法(資料型別、變數) - part 2
【JavaScript 筆記】語法(資料型別、變數) - part 2
歡迎你點入本篇文章,本系列網頁程式設計,主要紀錄我個人自學的軌跡,另外也作為日後個人複習用。若你喜歡本篇文章,歡迎在文章底下點一顆愛心,或是追蹤我的個人公開頁~
資料型別(Data Type)

Image Source:https://www.geeksforgeeks.org/javascript/variables-datatypes-javascript/
JavaScript 中所有的值都屬於某種資料型別,型別分為兩大類:
- Primitive(原始型別)的值儲存的是值本身。
- Non-Primitive(非原始型別)儲存的是記憶體位址的參考(Reference)。
另外,JS 的語法也定義了兩個型別的值:
- Literals(實字):一個固定值,就是常數的意思。
- Variables(變數):隨時會變動的值。
用 typeof 查看型別
typeof 運算子可在 Console 中直接查看任何值的型別:

原始型別(Primitive)
1. Number(數字)
JS 的 Number 型別同時涵蓋整數與浮點數,底層都是 64 位元雙精度浮點數(IEEE 754 標準),安全整數範圍是 。
範例:
1 | let age = 21 // 整數 |
NaN 是非數字,但 typeof NaN 卻回傳 "number",這是 JS 著名的怪癖之一。
2. BigInt(大整數)
Number 型別無法精確表示超過 的整數,此時就要用 BigInt,在數字後面加上 n 即可宣告。

從上圖測試結果可看到:
9007199254740991 + 2的結果會是9007199254740992,應該要是9007199254740993才對,這代表已經超過Number的整數上限了。- 也可看到 BigInt 輸出的結果會最後帶有一個 n:
9007199254740993n。 console.log(10n + 5)代表 BigInt 跟 Number 是不能相加的。
3. String(字串)
用來表示文字,可以用單引號、雙引號或反引號包起來。
範例:
1 | let s1 = 'Hello' // 單引號 |
實際執行畫面:

4. Boolean(布林值)
只有兩個可能的值:true(真)或 false(假),是所有判斷式與流程控制的核心。
範例:
1 | let isLoggedIn = true |
實際執行畫面:

Falsy 值:以下這些值在布林判斷中都被視為 false:
1 | Boolean(0) // false |
反之,以上六個以外的所有值,都是 truthy(被視為 true)。
5. Null(空值)
null 在 JS 裡面是一種原始值,表示沒有值。
範例:
1 | let user = null |
typeof null 回傳 "object" 是 JS 的歷史遺留 bug,實際上 null 是獨立的原始型別,不是物件。
6. Undefined(未定義)
undefined 代表變數被宣告了,但還沒被賦值,是 JS 自動給予的預設值 。
範例:
1 | let x // 宣告但未賦值 |
Null vs Undefined
| null | undefined | |
|---|---|---|
| 意思 | 刻意設為空 | 還沒被賦值 |
| 誰設定的 | 程式設計師 | JS 引擎 |
| 使用情境 | 主動清空一個變數 | 尚未初始化 |
| typeof | "object" | "undefined" |
7. Symbol(符號)
Symbol 是 ES6 新增的型別,用來建立全域唯一的識別字,即使描述相同的兩個 Symbol 也不相等。
範例:
1 | let id1 = Symbol("id") |
Symbol 主要出現在設計框架、函式庫或需要嚴格避免 key 碰撞的場景。
非原始型別(Non-Primitive)
非原始型別又稱參考型別(Reference Type),變數儲存的不是值本身,而是指向記憶體中資料的位址。
1. Object(物件)
物件是用來儲存一組相關資料與功能的容器,以鍵值對(key-value pair)的形式組織 。
1 | // 建立物件 |
2. Arrays(陣列)
陣列是有順序的資料集合,用中括號 [] 表示,每個元素用索引(Index)存取,從 0 開始計算。
1 | // 建立陣列 |
3. Function(函式)
函式是可以重複執行的程式碼區塊,可以被存進變數、當參數傳遞。
1 | // 函式宣告 |
原始型別(Primitive) vs 非原始型別(Non-Primitive)
1 | // 原始型別: 複製值, 互不影響 |
| 特性 | Primitive | Non-Primitive |
|---|---|---|
| 儲存的是 | 值本身 | 記憶體位址(參考) |
| 複製後 | 各自獨立 | 共用同一份資料 |
| 比較方式 | 比較值 | 比較記憶體位址 |
| 可變性 | 不可變(Immutable) | 可變(Mutable) |
變數(Variables)
變數(Variable)是用來替記憶體中某塊空間取名字的,方便用於儲存與重複使用資料。
在 JS 中,宣告變數有三種關鍵字:var、let、const 。
1. var(舊式,不推薦)
var 是 ES6(2015)以前唯一的宣告方式,但它有幾個令人困惑的特性,現代開發幾乎已棄用。
語法:
1 | var 變數名稱 = 值 |
特性一:函式作用域(Function Scope)
var 的有效範圍是整個函式或全域,而不是 {} 區塊,表示在 if、for 等區塊內宣告的 var,外面也看得到:
1 | if (true) { |
用我們一般學過程式語言的知識來說,這樣存取應該是存取不到的,但卻可以。
特性二:Hoisting(提升)
JS 引擎在執行前,會先把 var 的宣告移到最頂端(但不帶值),導致使用時機早於宣告卻不報錯,只會得到 undefined:
1 | console.log(x) // undefined(沒有報錯, 但還沒有值) |
實際上 JS 把上面的程式碼理解成:
1 | var x // ← 宣告被提升到頂端 |
實際的執行畫面:

特性三:可重複宣告
1 | var name = "LukeTseng" |
實際的執行畫面:

2. let(推薦)
ES6 推出的 let 解決了 var 的大部分問題,是現在最常用的宣告方式。
語法:
1 | let 變數名稱 = 值 |
特性一:區塊作用域(Block Scope)
有效範圍是 {} 包住的區塊,出了區塊就無法存取:
1 | if (true) { |
實際執行畫面:

特性二:有 Hoisting 但不初始化(TDZ)
let 也會被 Hoisting,但不會初始化為 undefined,在宣告前使用會直接報錯。
這段宣告前的禁區稱為 Temporal Dead Zone(TDZ,暫時性死區):
1 | console.log(y) // ReferenceError: Cannot access 'y' before initialization |
實際執行畫面:

特性三:不能重複宣告,但可以重新賦值
1 | let score = 80 |
3. const(宣告常數)
const 用來宣告不會再被重新賦值的變數,宣告時必須立刻給值。
語法:
1 | const 變數名稱 = 值 |
範例:
1 | const PI = 3.14159 |
const 阻止的是重新賦值,不是值的內容被修改,如果 const 存的是物件或陣列,其內部的屬性仍然可以修改:
1 | const user = { name: "Luke", age: 19 } |
實際執行畫面:

var / let / const 比較
| 特性 | var | let | const |
|---|---|---|---|
| 作用域 | 函式作用域或全域 | 區塊作用域 | 區塊作用域 |
| Hoisting | 初始化為 undefined | TDZ,提早存取報錯 | TDZ,提早存取報錯 |
| 重複宣告 | ✓可以 | ✗不行 | ✗不行 |
| 重新賦值 | ✓可以 | ✓可以 | ✗不行 |
| 宣告時需給值 | 不需要 | 不需要 | 必須 |
| 現代推薦程度 | 不推薦 | 優先使用 | 優先使用 |
變數名稱規則(識別字)
識別字(Identifier)就是幫變數、函式取的名字,然後 JS 對於變數名稱有以下硬性規則:
- 只能包含:英文字母(a-z、A-Z)、數字(0-9)、底線(
_)、錢字號($)。 - 不能以數字開頭。
- 大小寫有差異(
name和Name是不同的變數)。 - 不能是關鍵字(如
let、const、if、return等)。
以下是合法與非法的變數識別字範例:
1 | // 合法 |
命名慣例(非強制,但業界共識):
1 | // 變數、函式 → camelCase(小駝峰) |
一行多變數宣告
1 | // 宣告多個變數, 同時賦值 |
JS 是弱型別的程式語言
一些編譯式語言,如 C、C++ 等,都是強型別的程式語言,在宣告變數時一定要指定資料型別,如 C++ 寫法:
1 | int age = 21; |
JavaScript 完全不需要,因為它是弱型別(Weakly Typed)+動態型別(Dynamically Typed)的語言:
- 動態型別:變數的型別在執行時自動判斷,不需事先宣告。
- 弱型別:不同型別的值可以自動轉換互相運算(隱式型別轉換)。
1 | // 同一個變數,型別可以隨時改變 |
總整理
JavaScript 中的值分為兩大類別,並且可以透過 typeof 運算子來檢查任何值的型別:
- Primitive(原始型別):變數直接儲存值本身,複製時各自獨立,互不影響(不可變)。
- Non-Primitive(非原始型別 / 參考型別):變數儲存的是記憶體位址,複製時會共用同一份資料,牽一髮動全身(可變)。
另外本篇提到的其他兩個名詞:
- Literals(實字):程式碼中寫死的固定值(常數)。
- Variables(變數):用來儲存值、隨時可變動的容器。
原始型別(Primitive Types)
- Number(數字):
- 涵蓋整數與浮點數(底層皆為 64 位元浮點數)。
- 安全整數範圍是 。
- 包含特殊值
Infinity與NaN。 - 注意:
typeof NaN的結果為"number"。
- BigInt(大整數):專門處理超過 的巨大整數,宣告時需在數字後方加上 n(例如 10n)。
- 無法直接與 Number 型別混合運算。
- String(字串):文字型別,使用單引號、雙引號或反引號包覆。
- 反引號(樣板字串)支援
${}嵌入變數。
- 反引號(樣板字串)支援
- Boolean(布林值):僅有
true與false,是流程控制的核心。- 在 JS 中會被判定為
false的 Falsy 值只有六個:0""(空字串)nullundefinedNaNfalse
- 在 JS 中會被判定為
- Null(空值):開發者刻意設定的空值。
- 注意:
typeof null回傳"object"是 JS 的歷史遺留 Bug。
- 注意:
- Undefined(未定義):變數已宣告但尚未賦值時,JS 引擎自動給予的預設狀態。
- Symbol(符號):ES6 新增,用來建立全域唯一的識別字,最常用於物件的唯一屬性 Key,避免命名衝突。
非原始型別(Non-Primitive Types)
- Object(物件):以鍵值對(key-value pair)組合而成的資料容器。
- 可透過點記法(
obj.key)或括號記法(obj["key"])存取與修改屬性。
- 可透過點記法(
- Array(陣列):有順序的資料集合,使用
[]宣告,索引值從 0 開始。typeof檢查陣列會回傳"object",需改用Array.isArray()來精確判斷。
- Function(函式):可重複執行的程式碼區塊。
- 分為函式宣告、運算式與 ES6 箭頭函式(
=>)。
- 分為函式宣告、運算式與 ES6 箭頭函式(
變數(Variables)宣告
JavaScript 提供三種宣告變數的方式,現代開發強烈建議棄用 var,優先使用 let 與 const。
| 特性 | var | let | const |
|---|---|---|---|
| 作用域 | 函式作用域或全域 | 區塊作用域 | 區塊作用域 |
| Hoisting | 初始化為 undefined | TDZ,提早存取報錯 | TDZ,提早存取報錯 |
| 重複宣告 | ✓可以 | ✗不行 | ✗不行 |
| 重新賦值 | ✓可以 | ✓可以 | ✗不行 |
| 宣告時需給值 | 不需要 | 不需要 | 必須 |
| 現代推薦程度 | 不推薦 | 優先使用 | 優先使用 |
關於 const 的重要觀念:const 拒絕的是重新賦值的動作,若 const 儲存的是物件或陣列(參考型別),其內部的屬性或元素依然可以被新增、修改或刪除。
變數命名規則與 JS 語言特性
- 命名規則:只能包含大小寫英文字母、數字、底線(
_)與錢字號($),不能以數字開頭、區分大小寫,且不可使用系統保留關鍵字。 - 業界命名慣例:
- 變數與函式使用小駝峰(camelCase)
- 類別使用大駝峰(PascalCase)
- 常數使用全大寫加底線(MAX_SIZE)。
- 動態弱型別特性:JavaScript 不需事先宣告資料型別(動態型別),且不同型別的值互相運算時,會自動進行隱式型別轉換(弱型別),例如
"5" + 3會變成字串"53",而"5" - 3則會算出數字2。
參考資料
Variables and Datatypes in JavaScript - GeeksforGeeks
Rules for naming variables in JavaScript - DEV Community
Mastering JavaScript Naming Conventions: 10 Best Practices for Cleaner Code | Syncfusion Blogs



