第十章:高级类型工具

TypeScript 提供了许多内置的高级类型工具,可以帮助我们更方便地操作和转换类型。

对象类型工具

Partial

将类型 T 的所有属性变为可选:

interface User {
    id: number;
    name: string;
    age: number;
}

type PartialUser = Partial<User>;
// 等价于:
// {
//     id?: number;
//     name?: string;
//     age?: number;
// }

使用场景:

  • 更新对象的部分属性
  • 表单数据处理
  • API 请求参数

Required

将类型 T 的所有属性变为必需:

interface PartialUser {
    id?: number;
    name?: string;
    age?: number;
}

type CompleteUser = Required<PartialUser>;
// 等价于:
// {
//     id: number;
//     name: string;
//     age: number;
// }

使用场景:

  • 确保所有属性都被提供
  • 数据验证
  • 配置对象

Readonly

将类型 T 的所有属性变为只读:

interface Config {
    apiUrl: string;
    timeout: number;
}

type ReadonlyConfig = Readonly<Config>;
// 等价于:
// {
//     readonly apiUrl: string;
//     readonly timeout: number;
// }

使用场景:

  • 不可变数据
  • 配置对象
  • 常量定义

Record<K, T>

创建属性为 K 类型,值为 T 类型的对象类型:

type PageInfo = {
    title: string;
};

type Page = "home" | "about" | "contact";

type Nav = Record<Page, PageInfo>;
// 等价于:
// {
//     home: PageInfo;
//     about: PageInfo;
//     contact: PageInfo;
// }

使用场景:

  • 创建字典类型
  • 路由配置
  • 状态管理

Pick<T, K>

从类型 T 中选取一组属性 K

interface Todo {
    title: string;
    description: string;
    completed: boolean;
}

type TodoPreview = Pick<Todo, "title" | "completed">;
// 等价于:
// {
//     title: string;
//     completed: boolean;
// }

使用场景:

  • 选择对象的部分属性
  • 创建视图模型
  • API 响应过滤

Omit<T, K>

从类型 T 中排除一组属性 K

interface Todo {
    title: string;
    description: string;
    completed: boolean;
}

type TodoPreview = Omit<Todo, "description">;
// 等价于:
// {
//     title: string;
//     completed: boolean;
// }

使用场景:

  • 排除敏感属性
  • 创建简化类型
  • 数据脱敏

联合类型工具

Exclude<T, U>

从类型 T 中排除可以赋值给 U 的类型:

type T0 = Exclude<"a" | "b" | "c", "a">; // "b" | "c"
type T1 = Exclude<"a" | "b" | "c", "a" | "b">; // "c"
type T2 = Exclude<string | number | (() => void), Function>; // string | number

使用场景:

  • 从联合类型中移除特定类型
  • 类型过滤
  • 条件类型

Extract<T, U>

从类型 T 中提取可以赋值给 U 的类型:

type T0 = Extract<"a" | "b" | "c", "a" | "f">; // "a"
type T1 = Extract<string | number | (() => void), Function>; // () => void

使用场景:

  • 从联合类型中提取特定类型
  • 类型过滤
  • 条件类型

NonNullable

从类型 T 中排除 nullundefined

type T0 = NonNullable<string | number | undefined>; // string | number
type T1 = NonNullable<string[] | null | undefined>; // string[]

使用场景:

  • 移除可能为空的类型
  • 确保类型不为空
  • 安全的类型操作

函数类型工具

Parameters

获取函数类型的参数类型:

type T0 = Parameters<() => string>; // []
type T1 = Parameters<(s: string) => void>; // [string]
type T2 = Parameters<<T>(arg: T) => T>; // [unknown]

使用场景:

  • 提取函数参数类型
  • 创建高阶函数
  • 函数类型转换

ConstructorParameters

获取构造函数类型的参数类型:

class Person {
    constructor(name: string, age: number) {}
}

type PersonConstructorParams = ConstructorParameters<typeof Person>;
// [name: string, age: number]

使用场景:

  • 提取构造函数参数
  • 工厂函数
  • 依赖注入

ReturnType

获取函数类型的返回类型:

type T0 = ReturnType<() => string>; // string
type T1 = ReturnType<(s: string) => void>; // void
type T2 = ReturnType<<T>() => T>; // unknown

使用场景:

  • 提取函数返回类型
  • 类型推断
  • 函数组合

InstanceType

获取构造函数类型的实例类型:

class Person {
    name: string;
    constructor(name: string) {
        this.name = name;
    }
}

type PersonInstance = InstanceType<typeof Person>;
// Person

使用场景:

  • 获取类的实例类型
  • 工厂模式
  • 依赖注入

ThisParameterType

获取函数类型的 this 参数类型:

function toHex(this: Number) {
    return this.toString(16);
}

type ToHexThisType = ThisParameterType<typeof toHex>;
// Number

使用场景:

  • 提取 this 类型
  • 函数绑定
  • 方法借用

OmitThisParameter

从函数类型中移除 this 参数:

function toHex(this: Number) {
    return this.toString(16);
}

type ToHexWithoutThis = OmitThisParameter<typeof toHex>;
// () => string

使用场景:

  • 移除 this 参数
  • 函数转换
  • 方法解耦

字符串类型工具

Uppercase

将字符串类型转为大写:

type T0 = Uppercase<"hello">; // "HELLO"

Lowercase

将字符串类型转为小写:

type T0 = Lowercase<"HELLO">; // "hello"

Capitalize

将字符串类型的首字母大写:

type T0 = Capitalize<"hello">; // "Hello"

Uncapitalize

将字符串类型的首字母小写:

type T0 = Uncapitalize<"Hello">; // "hello"

使用场景:

  • 字符串类型转换
  • 命名规范
  • 类型安全的字符串操作

类型工具总结

类型工具 作用 使用场景
Partial 属性变可选 部分更新
Required 属性变必需 数据验证
Readonly 属性变只读 不可变数据
Record 创建对象类型 字典类型
Pick 选取属性 视图模型
Omit 排除属性 数据脱敏
Exclude 排除类型 类型过滤
Extract 提取类型 类型过滤
NonNullable 移除 null/undefined 类型安全
Parameters 获取参数类型 函数类型转换
ConstructorParameters 获取构造参数 工厂函数
ReturnType 获取返回类型 类型推断
InstanceType 获取实例类型 依赖注入
Uppercase 转大写 命名规范
Lowercase 转小写 命名规范
Capitalize 首字母大写 命名规范
Uncapitalize 首字母小写 命名规范

最佳实践

  1. 组合使用类型工具:多个类型工具可以组合使用
  2. 创建可复用的类型:将常用的类型操作提取为类型别名
  3. 保持类型简单:避免过度复杂的类型操作
  4. 理解类型工具的实现:有助于更好地使用它们
  5. 使用类型工具提高类型安全性:减少运行时错误
  6. 文档化复杂类型:为复杂的类型添加注释
Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐