Skip to content

映射类型

in 关键字

在映射类型中遍历联合类型的每一个成员

结合[key in keyof T] 实现泛型键名遍历更改

ts
// key 类型限制为string
type Foo = {
  [key: string]: string;
};
// 通过in 限定key 为"id”或“name”
type Foo = {
  [key in "id" | "name"]: string;
};
/**
 * 通过keyof 获取User 的key 的联合类型,然后UserKeys 的key 限定为User 的key
 */
type User = {
  id: number;
  name: string;
  age: number;
};
type UserKeys = {
  [key in keyof User]: string;
};
/**
 * 包含修饰符情况
 */
type Person = {
  readonly id: number;
  name: string;
  age?: number;
};
type PersonKeys = {
  [key in keyof Person]: Person[key];
};
// { readonly id: string; name: string; age?: string; }
/**
 * 通用性
 */
type CopyKeys<T extends object> = {
  [key in keyof T]: T[key];
};

映射类型修饰符

属性修饰符(readonly?)

ts
type Person = {
  id: number;
  name: string;
  age: number;
};
// 添加只读属性
type ReadonlyPersonKeys = {
  readonly [key in keyof Person]: Person[key];
};
// 添加可选属性
type OptionalPersonKeys = {
  [key in keyof Person]+?: Person[key];
};

修饰操作符(+-)

ts
type Person = {
  readonly id: number;
  name: string;
  age?: number;
};
// 只读属性通过"-readonly"、可选属性通过"-?",移除。
type PersonKeys = {
  -readonly [key in keyof Person]-?: Person[key];
};

as 关键字

结合模板字符串类型实现键名重映射

结合extends 条件类型实现键名属性过滤

ts
// 原始类型
type User = {
  readonly id: number;
  name: string;
  tel: string;
  address: string;
};
// 类似官方工具:Omit<T, K>
type Filter<T, K> = {
  [P in keyof T as P extends K ? never : P]: T[P];
};
/* 解析
    P in keyof T,id | name | tel | address
    P extends K ? never : P,返回K 中没有的P,实现过滤
*/
type UserFilter = Filter<User, "id" | "tel">; // { name: string; address: string; }
// 类似:提取所有string 类型的属性
type StringFilter<T> = {
  [P in keyof T as T[P] extends string ? P : never]: T[P];
};
type UserStringFilter = StringFilter<User>; // { name: string; address: string; }
// 类似:提取指定类型的属性
type FilterByType<T, U> = {
  [P in keyof T as T[P] extends U ? P : never]: T[P];
};

Released under the MIT License.