TypeScript - Utility Types
你好,未來的編程巫師們!今天,我們將踏上一段令人興奮的旅程,探索 TypeScript 的神奇領域:Utility Types。別擔心如果你是編程新手;我將成為你的友好導遊,我們將一起逐步探索這些概念。所以,拿起你的虛擬魔杖(鍵盤),讓我們一起深入探訪!
Utility Types 是什麼?
在我們開始之前,讓我們先了解什麼是 Utility Types。想像一下你有一個裝滿各種工具的工具箱。每個工具都能幫助你更有效率地完成特定任務。這正是 TypeScript 中的 Utility Types —— 它們是預先建造的工具,幫助我們輕鬆地操作和轉換類型。
現在,讓我們一一看看這些神奇的工具!
TypeScript 中的 Partial Type
Partial 類型就像一個魔法,它使物件中的所有屬性變為可選。當你想創建一個不需要指定所有屬性的物件時,它非常有用。
讓我們看看它是如何運作的:
interface Wizard {
name: string;
age: number;
house: string;
}
function updateWizard(wizard: Wizard, fieldsToUpdate: Partial<Wizard>) {
return { ...wizard, ...fieldsToUpdate };
}
const harryPotter: Wizard = {
name: "Harry Potter",
age: 11,
house: "Gryffindor"
};
const updatedHarry = updateWizard(harryPotter, { age: 17 });
console.log(updatedHarry);
// 輸出: { name: "Harry Potter", age: 17, house: "Gryffindor" }
在這個例子中,Partial<Wizard>
讓我們能夠只更新 Harry 的年齡,而不需要指定其他所有屬性。這就像揮動魔杖並說,“部分顯現魔法!”
TypeScript 中的 Required Type
Required 類型是 Partial 的相反。它就像施展一個魔法,使物件中的所有屬性都變為必填,即使它們原本是可選的。
interface MagicalCreature {
name: string;
power?: string;
age?: number;
}
const dragon: Required<MagicalCreature> = {
name: "Norwegian Ridgeback",
power: "Fire Breath",
age: 2
};
// 這會導致錯誤:
// const unicorn: Required<MagicalCreature> = {
// name: "Silver Horn"
// };
在這裡,即使原始接口中的 power
和 age
是可選的,Required 類型也使它們變為必填。這就像說,“召喚所有屬性!”
TypeScript 中的 Pick Type
Pick 類型允許你從現有的類型中選擇特定的屬性來創建一個新的類型。這就像使用召喚咒語來呼唤你需要的屬性。
interface Potion {
name: string;
ingredients: string[];
brewingTime: number;
effect: string;
}
type PotionLabel = Pick<Potion, 'name' | 'effect'>;
const polyjuicePotion: PotionLabel = {
name: "Polyjuice Potion",
effect: "Transforms the drinker into another person"
};
在這個例子中,我們創建了一個新的類型 PotionLabel
,它只包括 Potion
接口中的 name
和 effect
屬性。這對於当你只需要幾個特定細節時非常完美!
TypeScript 中的 Omit Type
Omit 類型是 Pick 的相反。它通過從現有的類型中刪除特定的屬性來創建一個新的類型。這就像對某些屬性施展消失咒!
interface SpellBook {
title: string;
author: string;
pages: number;
secretSpell: string;
}
type PublicSpellBook = Omit<SpellBook, 'secretSpell'>;
const beginnerSpellBook: PublicSpellBook = {
title: "Standard Book of Spells, Grade 1",
author: "Miranda Goshawk",
pages: 250
};
在這裡,我們創建了一個 PublicSpellBook
類型,它包括 SpellBook
的所有屬性,除了 secretSpell
。這就像說,“除了秘密,顯示一切!”
TypeScript 中的 Readonly Type
Readonly 類型就像對你的屬性施加一個保護咒語。它使類型中的所有屬性變為唯讀,防止意外修改。
interface Wand {
wood: string;
core: string;
length: number;
}
const harryWand: Readonly<Wand> = {
wood: "Holly",
core: "Phoenix feather",
length: 11
};
// 這會導致錯誤:
// harryWand.length = 12;
使用 Readonly,我們確保一旦創建了魔杖,其屬性就不能被更改。這就像在對象上施加一個不可摧壞的咒語!
TypeScript 中的 ReturnType Type
ReturnType 效用類型允許我們提取函數的返回類型。這就像使用顯形術來窺視函數並看它返回什麼!
function castSpell(spellName: string): { name: string, power: number } {
// 施法邏輯在這裡
return { name: spellName, power: Math.random() * 100 };
}
type SpellResult = ReturnType<typeof castSpell>;
const lumos: SpellResult = {
name: "Lumos",
power: 50
};
在這個例子中,SpellResult
被推导為 { name: string, power: number }
,這是 castSpell
的返回類型。這在處理複雜函數時非常有用!
TypeScript 中的 Record Type
Record 類型是一個強大的魔法,它創建一個具有特定鍵類型和值類型的物件類型。這就像召喚一個神奇的地圖,你定義鍵和值應該是什麼。
type HouseCup = Record<string, number>;
const housePoints: HouseCup = {
"Gryffindor": 472,
"Hufflepuff": 352,
"Ravenclaw": 426,
"Slytherin": 472
};
在這裡,HouseCup
是一個類型,其鍵是字符串(學院名稱),值是數字(積分)。它確保我們的學院積分物件具有正確的結構。
TypeScript 中的 NonNullable Type
NonNullable 類型就像施展一個魔法來驅逐 null 和 undefined 值。它通過從給定的類型中排除 null 和 undefined 來創建一個新的類型。
type MagicalItem = string | number | null | undefined;
type DefiniteMagicalItem = NonNullable<MagicalItem>;
const definiteItem: DefiniteMagicalItem = "Invisibility Cloak";
// 這會導致錯誤:
// const nullItem: DefiniteMagicalItem = null;
在這個例子中,DefiniteMagicalItem
是一個類型,可以是字符串或數字,但不能是 null 或 undefined。這在你想確保你正在使用實際值時非常完美!
Utility Types 速查表
這裡是我們討論過的所有 Utility Types 的快速參考表:
效用類型 | 描述 | 示例 |
---|---|---|
Partial |
使 T 中的所有屬性可選 | Partial<Wizard> |
Required |
使 T 中的所有屬性必填 | Required<MagicalCreature> |
Pick<T, K> | 從 T 中創建一個只包含 K 屬性的類型 | Pick<Potion, 'name' | 'effect'> |
Omit<T, K> | 從 T 中創建一個不包含 K 屬性的類型 | Omit<SpellBook, 'secretSpell'> |
Readonly |
使 T 中的所有屬性唯讀 | Readonly<Wand> |
ReturnType |
提取函數類型 T 的返回類型 | ReturnType<typeof castSpell> |
Record<K, T> | 創建一個具有鍵類型 K 和值類型 T 的物件類型 | Record<string, number> |
NonNullable |
通過從 T 中排除 null 和 undefined 來創建一個新的類型 | NonNullable<MagicalItem> |
年輕的巫師們,你現在已經掌握了 TypeScript Utility Types 的基本咒語。記住,就像任何魔法一樣,這些類型在練習中會變得更加強大。所以,繼續實驗,很快你就能像說“Wingardium Leviosa”一樣輕鬆施展這些類型!
Credits: Image by storyset