iT邦幫忙

2023 iThome 鐵人賽

DAY 16
0
Modern Web

TypeScript 啟動!系列 第 16

[Day 16] TypeScript 進階型別

  • 分享至 

  • xImage
  •  

TypeScript 提供強大的型別系統,在今天我們會介紹幾個特別常見的物件型別、函式型別和條件式型別的簡單運用。

型別運算子

TypeScript 中型別運算子允許基於一些現有的型別,來建立新的型別。常見的如, keyoftypeof 等。

interface Person {
  name: string;
  age: number;
}

type Keys = keyof Person; // "name" | "age"

例如我們在建立一個新的型別( interface )上,而這個介面的元素有 name 和 age,也就是說我們使用的 keyof 之後就能得出其元素有 name 和 age 兩個,未來就能動態獲取物件的 key 了。

Record 型別

TypeScript 中的 Record 可以幫助我們創建一個物件,其中 key 和 value 都有特定的型別。

type Weekdays = "Mon" | "Tue" | "Wed" | "Thu" | "Fri";
type Status = "Open" | "Closed";

const storeStatus: Record<Weekdays, Status> = {
  Mon: "Open",
  Tue: "Open",
  Wed: "Open",
  Thu: "Closed",
  Fri: "Open",
};

例如我們應用在店家營業,代表 key 只有週一到週五(週休二日),value 則會有營業跟休息的情況下就能這樣子使用。

映射型別(key value)

TypeScript 中映射型別可以允許我們將一個現有型別轉換成另一種型別,如下。

type ReadOnly<T> = {
  readonly [P in keyof T]: T[P];
};

type Person = {
  name: string;
  age: number;
};

type ImmutablePerson = ReadOnly<Person>;

首先我們先建立一個型別為 ReadOnly 的,其中泛型大家還記得吧,也就是說裡面的 P 將會屬於 T裡面,也就是 string 或 number 並且變成一個陣列物件,而這個陣列物件只能含有 string 或 number。

伴隨物件模式

這個比較特別,屬於使用 TypeScript 中的映射型別功能來實現類似匹配的功能。

type Action =
  | { type: "INCREMENT"; amount: number }
  | { type: "DECREMENT"; amount: number };

const handleAction = (action: Action) => {
  switch (action.type) {
    case "INCREMENT":
      return action.amount;
    case "DECREMENT":
      return -action.amount;
  }
};

我們首先宣告一個 Action 的型別,其中根據他的型別(模式)來進行回傳不同的資料,例如傳入 action.type == DECREMENT 的話,我們就讓數字變成負數吧。這就可以應用在一些參數雷同但是針對某個元素不同而有不同的操作應用上應該很不錯。

函式型別

在 TypeScript 中允許我們為函式參數和回傳值進行指定型別的操作。

type HiFunction = (name: string) => string;
const Hi: HiFunction = (name) => `Hello, ${name}!`;

我們也能針對函示去定義型別,代表參數只能字串,回傳也是字串,應該蠻容易理解的。這可以應用在為了確定更清晰的 API 定義的時候。

條件式型別

在 TypeScript 中允許我們針對某個條件來選擇型別。

type IsString<T> = T extends string ? true : false;

type X = IsString<string>; // true
type Y = IsString<number>;  // false

代表如果是字串的話,型別就會是 true 。可以根據指定的判別式來進行。有點類似寫了一個函式的感覺,可以用於許多型別檢查或型別過濾的情境。

這些進階型別可以提供在開發上的讓整件事情的型別定義上來的更加彈性化跟清晰化,避免只是在處理應用於物件屬性等。而是能盡可能的把型別給定義好。


上一篇
[Day 15] TypeScript 泛型
下一篇
[Day 17] TypeScript 處理錯誤
系列文
TypeScript 啟動!30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言