# 認識 TypeScript 自從學習了 JavaScript 後就聽說了叫 TypeScript 的程式語言。 所以找了資料做一些整理來認識一下 TypeScript ,方便學習上更好吸收。 ## TypeScript 是什麼 ? Typescript 是一種由 Microsoft 開發的開源程式語言。是 JavaScript 的型別的超集,它可以編譯成純 JavaScript。編譯出來的 JavaScript 可以執行在任何瀏覽器上。TypeScript 編譯工具可以執行在任何伺服器和任何系統上。TypeScript 是開源的。 ### 為什麼要學 TypeScript? * 可以幫你提早發現錯誤 * 讓你的程式更穩定、更容易維護 * 在大型團隊開發時,大家用一致的型別規則會比較不容易踩雷 * 很多主流框架像 **React**、**Vue** 也都推薦使用 TypeScript #### TypeScript 跟 JavaScript 的差異是什麼? 比較項目 | JavaScript | TypeScript | -------- | -------- | -------- | 型別檢查 | 沒有型別限制,錯誤要等跑起來才知道 | 有靜態型別檢查,寫程式時就會提示錯誤 語法自由度 | 非常自由,彈性高,但也容易出錯 | 更嚴謹,讓大型專案更好管理 編譯執行 | 直接執行在瀏覽器或 Node.js 中 | 需先轉換(編譯)成 JavaScript 才能執行 IDE 支援 | 基本提示 | 更好的自動補全、型別提示 適用場景 | 小專案、快速開發 | 中大型專案、多人合作時更安全可靠 直接理解 TypeScript 是 JavaScript 的加強版,也因為超集 TypeScript 包含了 JavaScript 的所有語法和功能,所以 * 會寫 JavaScript,就幾乎已經會寫 TypeScript。 * JavaScript 的語法在 TypeScript 裡面都可以用。 * 可直接修改副檔名,`.js` 檔案可以直接重新命名為 `.ts` 即可 * TypeScript 編譯出來的 JavaScript 可以執行在任何瀏覽器上並轉為「所有」瀏覽器看的懂得東西包含(ES5 語法)。 還有主要特色是「加上了**型別系統**或稱**靜態型別系統**」(Type System)」。 ## Type System 型別系統 Type System 就是幫變數、參數、函式等加上「資料型別」的規則,讓你可以清楚知道每個變數應該是什麼類型(例如是字串、數字、布林值等)。在寫錯型別時,編譯器會直接提醒你。 舉例來說 JavaScript 寫法: ```js function greet(name) { return "Hello, " + name; } greet(123); // 不會報錯,但結果是 "Hello, 123" ``` TypeScript 寫法: ```ts function greet(name: string): string { return "Hello, " + name; } greet(123); // 編譯時就會報錯:number 不是 string ``` 這就是 TypeScript 的強大之處 — 在你寫錯時就馬上提醒,而不是等到網頁壞掉才發現。 ### TypeScript 常見的型別(Primitive Types) | 型別 | 說明 | 範例 | | -------- | -------- | -------- | string | 文字字串 | ``"Hello"`` number | 數字(包含整數與小數) | `123`, `3.14` boolean | 布林值(真或假) | `true`, `false` array | 陣列 | `string[]`, `number[]` object | 物件(key-value 組合) | `{ name: "Amy", age: 18 }` any | 可以是任何型別(不建議濫用) | `let data: any = 123` unknown | 不確定型別(更安全的 any) | 需加判斷才能使用 null / undefined | 空值或未定義 | `let a: null = null` void | 沒有回傳值(常用在函式) | `function sayHi(): void {}` never | 永遠不會發生(例如拋錯的函式) | `function error(): never` tuple | 固定長度且型別順序固定的陣列 | `let x: [string, number]` enum | 列舉,讓值更有意義 | `enum Role { Admin, User }` 而型別系統又有著三種: 🔸 Type Annotation(型別註解) 意思是「手動指定變數或參數的型別」,這樣程式更清楚,也能避免錯誤。 範例: ```ts let name: string = "Amy"; let age: number = 25; let isOnline: boolean = true; function greet(name: string): void { console.log("Hi " + name); } ``` 這些 `: string`、`: number` 就是型別註解。 🔸 Type Inference(型別推論) TypeScript 很聰明,會根據你給的值自動判斷型別,不用你每次都寫註解。 範例: ```ts let msg = "Hello"; // TypeScript 自動推論 msg 是 string let count = 10; // 推論為 number ``` 不代表永遠不用寫型別,複雜結構還是建議加註解。 🔸 Type Assertion(型別斷言) 當你知道某個值的型別比 TypeScript 更清楚時,你可以強制告訴它是某個型別。 有兩種寫法: ```ts let someValue: unknown = "Hello World"; // 方法1:尖括號寫法(舊式) let strLength1: number = (<string>someValue).length; // 方法2:as 語法(建議) let strLength2: number = (someValue as string).length; ``` 這告訴 TypeScript:「這個值我知道它是 string,請當成 string 處理。」 概念 | 說明 | -------- | -------- | Type Annotation | 手動加型別 Type Inference | TypeScript 自己判斷型別 Type Assertion | 開發者強制告訴 TypeScript 它是什麼型別 ### Class 跟 Interface #### Class(類別) ➤ 用途: 用來建立「物件的模板」。可以用 class 來定義某種東西的屬性(變數)與方法(函式),就像在定義「一種東西」的樣子。 範例: ```ts class Person { name: string; age: number; constructor(name: string, age: number) { this.name = name; this.age = age; } sayHello() { console.log(`Hi, I'm ${this.name}, ${this.age} years old.`); } } const tom = new Person('Tom', 25); tom.sayHello(); ``` ➤ 重點: `constructor` 是用來初始化物件的。 使用 new 建立物件實體(instance)。 可以加上修飾詞(public, private, protected)控制變數的使用範圍。 #### Interface(介面) ➤ 用途: 用來定義「型別的結構」,先訂好一個「規則」,哪些欄位是必要的、資料型別是什麼,但不會實作內容。常用來描述物件型別或規範 class 要有哪些內容。 範例: ```ts interface PersonInfo { name: string; age: number; } function printInfo(p: PersonInfo) { console.log(`${p.name} is ${p.age} years old.`); } const jane = { name: 'Jane', age: 30 }; printInfo(jane); ``` #### Interface 搭配 class: ```ts interface CanFly { fly(): void; } class Bird implements CanFly { fly() { console.log("Flapping wings..."); } } ``` **注意事項** * Interface 不能實作方法,只能定義結構。 * Class 裡的屬性必須符合 Interface 的規則(若用了 implements)。 * Class 裡的屬性與方法,一定要跟 interface 中定義的屬性與方法「一模一樣」才能通過編譯。 * Interface 可用來描述函式、陣列、物件結構,非常靈活。 * Interface 與 Type alias (type) 功能上有重疊,但 interface 比較適合擴充型別。 ## 總結 學習過後,粗略的做了整理。 TypeScript 學起來不算完全輕鬆,尤其是剛接觸會被型別系統卡住與 Class 跟 Interface 的不熟悉。 但能提早發現拼錯屬性名、資料格式不對、傳錯參數這些問題,減少除錯時間。與主流框架 React、Vue 的推薦使用,就是好好學習 TypeScript 的理由了。 ### 參考資料 * https://www.typescriptlang.org/ * https://willh.gitbook.io/typescript-tutorial/introduction/get-typescript * https://vocus.cc/article/6466032cfd89780001cb03d1 * https://summer10920.github.io/2021/08-25/typescript/