【TypeScript】条件类型

TypeScript 条件类型(Conditional Types)是一种高级类型工具,允许基于一个条件来选择两种不同的类型之一。条件类型的使用通常结合泛型类型参数,能够在类型系统中进行复杂的条件分支操作。条件类型的通用形式如下:

typescript 复制代码
T extends U ? X : Y
  • T 是待检查的类型。
  • U 是要检查是否可分配给 T 的类型。
  • 如果 T 可以赋值给 U,则条件类型的结果是 X,否则是 Y

1、可选属性的条件类型

考虑一个使用条件类型来创建可选属性的示例:

typescript 复制代码
type MakePropertyOptional<T, K extends keyof T> = {
    [P in K]: T[P];
} & {
    [P in Exclude<keyof T, K>]?: T[P];
};

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

type UpdatedType = MakePropertyOptional<OriginalType, 'age'>;

定义了一个条件类型 MakePropertyOptional,它接受两个类型参数:T 是原始类型,K 是属性名的联合类型。它的工作原理如下:

  • MakePropertyOptional<OriginalType, 'age'>OriginalType 的属性按照 K 的分组分为两部分,一部分包括 age 属性,另一部分包括其余属性。
  • age 属性保持不变,而其他属性被标记为可选(?)。

2、联合类型的条件类型

考虑一个使用条件类型来过滤联合类型的示例:

typescript 复制代码
type FilterByType<T, U> = T extends U ? T : never;

type OriginalUnion = string | number | boolean;
type FilteredUnion = FilterByType<OriginalUnion, string>;

在这个示例中,FilterByType 条件类型将筛选出 OriginalUnion 联合类型中的符合条件的类型。在这里,我们只选择了字符串类型,所以 FilteredUnion 的类型将是 string

3、根据条件选择返回类型

这个示例演示了如何使用条件类型根据条件选择返回类型:

typescript 复制代码
type If<Condition extends boolean, Then, Else> = Condition extends true ? Then : Else;

type Result = If<true, 'Yes', 'No'>; // Result 类型为 'Yes'

If 是一个自定义条件类型,它根据 Condition 参数的值返回 ThenElse 中的一个。在这里,由于条件是 true,所以 Result 的类型是 'Yes'

这些示例展示了 TypeScript 条件类型的多种应用,包括属性操作、类型过滤和条件分支。它们允许你在类型级别进行复杂的判断和操作,提高了代码的类型安全性和可读性。 当使用 TypeScript 的条件类型时,你可以执行许多复杂的类型操作。以下是更多示例,每个示例都详细描述其目的和工作原理:

4、从对象类型中提取特定属性类型

假设你有一个包含不同属性类型的对象,并且你想从中提取特定属性的类型。你可以使用条件类型来实现这一点:

typescript 复制代码
type ExtractPropertyType<T, K> = T extends { [key: string]: infer U } ? U : never;

type MyObject = {
    name: string;
    age: number;
    isValid: boolean;
};

type AgeType = ExtractPropertyType<MyObject, 'age'>; // AgeType 类型为 number

在这个示例中,ExtractPropertyType 条件类型根据属性名 K 从对象类型 T 中提取对应属性的类型。

5、根据条件从联合类型中排除特定类型

有时你可能想从联合类型中排除特定的类型。条件类型可以帮助你实现这一点:

typescript 复制代码
type ExcludeType<T, U> = T extends U ? never : T;

type OriginalUnion = string | number | boolean;
type WithoutNumbers = ExcludeType<OriginalUnion, number>;

在这个示例中,ExcludeType 条件类型将从 OriginalUnion 联合类型中排除了 number 类型,所以 WithoutNumbers 的类型将是 string | boolean

6、根据数组元素类型构建新数组类型

你可以使用条件类型来构建新数组类型,其中的每个元素类型都是给定类型的属性类型:

typescript 复制代码
type ArrayElementType<T> = T extends (infer U)[] ? U : never;

type MyArray = [string, number, boolean];
type Element = ArrayElementType<MyArray>; // Element 类型为 string | number | boolean

在这个示例中,ArrayElementType 条件类型将从数组类型 T 中提取元素类型,这对于操作数组类型非常有用。

7、使用条件类型进行函数参数检查

条件类型可以用于检查函数的参数类型,并根据不同的条件执行不同的操作:

typescript 复制代码
type CheckParams<T> = T extends (...args: infer Args) => any
    ? Args
    : never;

function printLength(arr: number[]) {
    const length = arr.length;
    console.log(`Array length: ${length}`);
}

type Params = CheckParams<typeof printLength>; // Params 类型为 [number[]]

在这个示例中,CheckParams 条件类型从函数类型 T 中提取参数类型。这可以用来在编译时检查函数的参数类型。

这些示例展示了 TypeScript 条件类型的更多应用,包括属性提取、类型排除、数组操作和函数参数检查。条件类型可以帮助你在类型级别执行复杂的操作,从而增强代码的类型安全性和可维护性。

相关推荐
MIka5 小时前
CopilotKit 入门:用 Runtime 和 React Core 搭建真正可用的 AI Copilot
人工智能·typescript·agent
学以智用5 小时前
# TypeScript 高级特性(核心+实用)
前端·javascript·typescript
学以智用5 小时前
TypeScript 核心基础:类型/变量 + 函数 + 接口
前端·javascript·typescript
蕨类植物5 小时前
Fastify 模块化项目实战(二) — 初始化Fastify 项目
typescript
蕨类植物5 小时前
Fastify 模块化项目实战 - 你真的懂 tsconfig.json 吗?
typescript
We་ct6 小时前
LeetCode 74. 搜索二维矩阵:两种高效解题思路
前端·算法·leetcode·矩阵·typescript·二分查找
回到原点的码农6 小时前
TypeScript 与后端开发Node.js
javascript·typescript·node.js
Irene19916 小时前
TypeScript 中,Pick 和 Omit 是两个非常常用且强大的内置工具类型(Utility Types)
typescript·pick·omit
江澎涌6 小时前
鸿蒙动态导入实战
android·typescript·harmonyos
SuperEugene1 天前
TypeScript+Vue 实战:告别 any 滥用,统一接口 / Props / 表单类型,实现类型安全|编码语法规范篇
开发语言·前端·javascript·vue.js·安全·typescript