TypeScript - 對映型別



TypeScript 中的對映型別用於透過轉換現有型別的屬性來建立新的型別。對映意味著在進行一些更改後,從現有元素建立新元素。類似地,對映型別意味著在對現有型別進行更改後建立新型別。因此,您可以重用現有型別來建立新型別。

內建對映型別

內建對映型別允許您轉換現有型別,而無需手動轉換型別。

以下是 TypeScript 中可用的內建對映型別。

  • Partial<T>:它透過使現有型別的所有屬性可選來建立新型別。

  • Required<T>:它透過使現有型別的所有屬性必填來建立新型別。

  • Readonly<T>:在新的型別中使所有屬性可選。

  • Record<K, T>:建立一個型別,其中包含一組型別為 T 的屬性 K。對於對映相同型別的屬性很有用。

  • Pick<T, K>:透過從 T 中選擇一組屬性 K 來建立新型別。

  • Omit<T, K>:透過從 T 中省略一組屬性 K 來建立新型別。

  • Exclude<T, U>:它透過排除可分配給 U 的 T 中的所有屬性來建立新型別。

  • Extract<T, U>:它透過提取可分配給 U 的 T 中的所有屬性來建立新型別。

  • NonNullable<T>:透過從 T 中排除 null 和 undefined 來構造一個型別。

示例

讓我們透過一些 TypeScript 程式示例來了解一些常用的內建對映型別。

示例:使用 Partial 型別

在下面的程式碼中,我們建立了包含 name 和 age 屬性的 Person 型別。之後,我們使用 Partial 實用程式型別從 Person 型別建立了一個新型別。

PartialPerson 型別具有 Person 類的所有屬性,但所有屬性都是可選的。我們定義了 PartialPerson 型別的 partialPerson 物件,它僅包含 name 屬性,因為所有屬性都是可選的。

// Creating the Person type
type Person = {
    name: string;
    age: number;
};

// Using the Partial mapped type
type PartialPerson = Partial<Person>;

// Creating an object of type PartialPerson
const partialPerson: PartialPerson = {
    name: "John",
    //   Age is optional
};
// Output
console.log(partialPerson);

編譯後,它將生成以下 JavaScript 程式碼。

// Creating an object of type PartialPerson
var partialPerson = {
    name: "John"
};
// Output
console.log(partialPerson);

輸出

{ name: 'John' }

示例:使用 ReadOnly 型別

在下面的程式碼中,我們使用 Readonly 實用程式型別建立了一個新型別,該型別具有 Person 型別的所有隻讀屬性。如果我們嘗試更改 partialPerson 物件的任何屬性,它將丟擲錯誤,因為它只讀。

// Creating the Person type
type Person = {
    name: string;
    age: number;
};

// Using the ReadOnly mapped type
type PartialPerson = Readonly<Person>;

// Creating an object of type PartialPerson
const partialPerson: PartialPerson = {
    name: "John",
    age: 30
};

// Trying to change the name property
// partialPerson.name = "Doe"; // Error: Cannot assign to 'name' because it is a read-only property.
// Output
console.log(partialPerson);

編譯後,它將生成以下 JavaScript 程式碼。

// Creating an object of type PartialPerson
const partialPerson = {
    name: "John",
    age: 30
};
// Trying to change the name property
// partialPerson.name = "Doe"; // Error: Cannot assign to 'name' because it is a read-only property.
// Output
console.log(partialPerson);

輸出

{ name: 'John', age: 30 }

示例:使用 Pick 型別

在下面的程式碼中,我們建立了 Animal 型別,它包含 3 個屬性。

之後,我們使用 Pick 實用程式型別僅從 Animal 型別中選擇 name 和 species 屬性,並建立一個名為 'AnimalNameAndSpecies' 的新型別。

animalNameAndSpecies 物件是 AnimalNameAndSpecies 型別,它僅包含 name 和 species 屬性。

// Creating the Animal type
type Animal = {
    name: string;
    species: string;
    age: number;
};
// Using the Pick utility type to create a new type
type AnimalNameAndSpecies = Pick<Animal, 'name' | 'species'>;
// Creating an object of the AnimalNameAndSpecies type
const animalNameAndSpecies: AnimalNameAndSpecies = {
    name: 'Milo',
    species: 'Dog'
};
console.log(animalNameAndSpecies);

編譯後,它將生成以下 JavaScript 程式碼。

// Creating an object of the AnimalNameAndSpecies type
const animalNameAndSpecies = {
    name: 'Milo',
    species: 'Dog'
};
console.log(animalNameAndSpecies);

輸出

{ name: 'Milo', species: 'Dog' }

建立自定義對映型別

實用程式函式的功能有限。因此,建立自定義對映型別以根據您自己的約定對映型別非常重要。

語法

您可以按照以下語法建立自定義對映型別。

type MyMappedType<T> = {
    [P in keyof T]: NewType;
};
  • 'T' 是我們需要從中建立新的自定義對映型別的現有型別。

  • 'P' 是型別的屬性。

  • 'keyof' 運算子獲取型別 'T' 的每個鍵。

  • NewType 是要分配給型別屬性 'P' 的新型別。

示例:使所有屬性都為布林值

在下面的程式碼中,我們建立了 Booleanify 型別,它將型別作為泛型引數。在型別主體內部,我們使用 '[P in keyof T]' 程式碼遍歷型別 'T' 的每個鍵,併為其分配一個布林值,因為我們正在將所有屬性的型別更改為布林值。

boolPerson 物件的所有屬性都是布林型別。

// Defining the Person type
type Person = {
  name: string;
  age: number;
};

// Creating the custom mapped type
type Booleanify<T> = {
    // Making all properties of Person type to Boolean
  [P in keyof T]: boolean;
};

// Creating an object of Booleanify type
const boolPerson: Booleanify<Person> = {
  name: true,
  age: true,
};
console.log(boolPerson);

編譯後,它將生成以下 JavaScript 程式碼

// Creating an object of Booleanify type
const boolPerson = {
    name: true,
    age: true,
};
console.log(boolPerson);

輸出

以上示例程式碼將產生以下輸出

{ name: true, age: true }

示例:使所有屬性都可選

在此示例中,我們無需使用內建實用程式型別 Partial 即可使現有型別的所有屬性都可選。

這裡,Animal 類包含 name 和 legs 屬性。在程式碼 [key in keyof Animal]?: Animal[key] 中,問號 (?) 使屬性可選,並且 Animal[key] 有助於保持屬性型別相同。

現在,在 customAnimal 物件中,所有屬性都是可選的。

// Defining the Animal type
type Animal = {
    name: string;
    legs: number;
};

// Creating custom type and making all properties optional using mapping
type CustomAnimal = {
    [key in keyof Animal]?: Animal[key];
};

// Creating an object of type CustomAnimal
let customAnimal: CustomAnimal = {
    name: "Dog",
    legs: 4,
};

console.log(customAnimal);

編譯後,它將生成以下 JavaScript 程式碼

// Creating an object of type CustomAnimal
let customAnimal = {
    name: "Dog",
    legs: 4,
};
console.log(customAnimal);

輸出

以上示例程式碼的輸出如下

{ name: 'Dog', legs: 4 }

您可以使用實用程式函式或建立自定義對映型別來重用現有型別以建立新型別。這些自定義對映型別提高了程式碼的可讀性,並幫助開發人員使程式碼易於維護。

廣告