TypeScript - 條件型別



在 TypeScript 中,條件型別允許您根據條件為變數賦值型別。這使您可以定義根據特定條件動態更改的型別。此功能對於大型應用程式非常有用,在大型應用程式中,您需要根據不同的情況進行動態型別設定。

基本條件型別

我們將使用三元運算子 (?:) 來使用條件型別。它將評估條件,並根據真或假的結果選擇新型別。

語法

您可以按照以下語法使用條件型別。

type A = Type extends anotherType ? TrueType : FalseType;
  • 在上述語法中,'Type extends anotherType' 條件將首先被評估。

  • 如果條件為真,則 'type A' 將包含 'TrueType'。否則,它將包含 'FalseType'。

  • 這裡,'extends' 關鍵字檢查 'Type' 是否與 'anotherType' 相同,或者至少包含 'anotherType' 型別的全部屬性。

示例

在下面的程式碼中,我們定義了包含 name、model 和 year 屬性的 'car' 型別。我們還定義了只包含 'name' 屬性的 'Name' 型別。

'carNameType' 型別變數根據 'Car extends Name' 條件的評估結果儲存字串或任何值。這裡,條件將被評估為真,因為 'Car' 型別包含 'Name' 型別的所有屬性。

之後,我們建立了 'carNameType' 型別的 'carName' 變數並在控制檯中列印它。

type Car = {
    name: string,
    model: string,
    year: number,
}
type Name = { name: string }
// If Car extends Name, then carNameType is string, otherwise it is any
type carNameType = Car extends Name ? string : any; // string
// Define a variable carName of type carNameType
const carName: carNameType = 'Ford';
console.log(carName); // Ford

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

// Define a variable carName of type carNameType
const carName = 'Ford';
console.log(carName); // Ford 

輸出

Ford

泛型條件型別

現在,讓我們學習泛型條件型別。在 TypeScript 中,泛型型別類似於函式中的引數。它允許開發人員定義條件型別,以便可以在程式碼中的多個位置使用它。它提供了在條件語句中使用不同型別的靈活性。

語法

您可以按照以下語法使用泛型條件型別。

type ConditionalType<T> = T extends Type1 ? TrueType : FalseType;
  • 在上述語法中,'conditionalType<T>' 有一個型別 'T' 引數,'conditionalType' 是型別的名稱。

  • 條件 'T extends Type1' 檢查型別 'T' 是否擴充套件 'Type1'。

  • 如果條件評估為真,則 'TrueType' 將被分配給 'ConditionalType'。否則,將分配 'FalseType'。

示例

在下面的程式碼中,'IsNumArray<T>' 是一個泛型型別,它將型別 'T' 作為引數。它檢查 'T' 的型別是否為數字陣列 (number[])。如果是,則返回 'number'。否則,返回 'string'。

之後,我們定義了 'num' 和 'str' 變數並使用它們與 'IsNumArray' 型別一起使用。對於 'num' 變數,我們使用了 'number[]' 引數;對於 'str' 變數,我們使用了 'string[]' 引數。

// Generic conditional types
type IsNumArray<T> = T extends number[] ? number : string;
const num: IsNumArray<number[]> = 5; // number
const str: IsNumArray<string[]> = '5'; // string
console.log(num);
console.log(str);

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

const num = 5; // number
const str = '5'; // string
console.log(num);
console.log(str);

輸出

5
5

條件型別約束

條件型別約束也稱為型別斷言或條件型別謂詞。它用於為泛型型別新增約束。泛型型別是可重用的,但是如果您想將它們重用於特定資料型別(如陣列、數字等),則應使用泛型型別新增約束。

語法

您可以按照以下語法使用條件型別約束。

type ConditionalType<T extends T1 | T2> = T extends Type1 ? TrueType : FalseType;

在上述語法中,我們為型別引數 'T' 添加了約束。它接受型別 'T1' 和 'T2' 的值。

示例

在下面的程式碼中,'CondionalType' 是一個泛型型別。它將數字或字串型別作為型別引數 'T' 的值。條件型別如果 'T' 的型別是數字,則返回數字。否則,返回字串。

接下來,我們透過傳遞數字和字串作為型別引數來重用 ConditionalType 型別。

您可以注意到,當我們嘗試使用 'boolean' 作為型別引數時,它會丟擲錯誤。因此,它允許使用有限型別的此泛型條件型別。

// Defining the conditional type with constraints
type ConditionalType<T extends number | string> = T extends number ? number : string;
let x: ConditionalType<number> = 10;
let y: ConditionalType<string> = 'Hello';
// let z: ConditionalType<boolean> = true; // Error: Type 'boolean' does not satisfy the constraint 'number | string'.
console.log("The value of x is: ", x);
console.log("The value of y is: ", y);

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

let x = 10;
let y = 'Hello';
// let z: ConditionalType<boolean> = true; // Error: Type 'boolean' does not satisfy the constraint 'number | string'.
console.log("The value of x is: ", x);
console.log("The value of y is: ", y);

輸出

The value of x is:  10
The value of y is:  Hello

在條件型別中推斷

在 TypeScript 中,在條件型別中推斷意味著使用條件型別定義來推斷型別。它允許您建立更靈活的型別轉換。

例如,如果您有一個元素陣列並將其與條件型別中的型別 'T' 匹配。之後,如果條件為真,您想返回陣列元素的型別,在這種情況下,推斷條件型別很有用。

語法

您可以使用 'infer' 關鍵字在條件型別中進行推斷。

type Flatten<Type> = Type extends Array<infer Item> ? Item : Type;

在上述語法中,'infer' 關鍵字用於提取陣列元素的型別。

示例

在下面的程式碼中,我們建立了 'Flatten' 條件型別。我們使用型別 'U' 使用 infer 關鍵字。它從具有型別 'U' 的元素陣列中提取 'U' 的型別。

對於 'Flatten<boolean>',它將返回一個布林值。因此,如果我們嘗試將字串值賦值給 'bool1' 變數,它將丟擲錯誤。

// Inferring within the conditional types
type Flatten<T> = T extends (infer U)[] ? U : T;
let bool: Flatten<boolean[]> = true;
// let bool1: Flatten<boolean> = "s"; // Error as string can't be assigned to boolean
console.log(bool);

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

let bool = true;
// let bool1: Flatten<boolean> = "s"; // Error as string can't be assigned to boolean
console.log(bool);

輸出

true

這樣,您就可以在 TypeScript 中使用條件型別。您可以使用泛型型別並推斷它們以使型別轉換更靈活。

廣告