TypeScript 常用的工具类型

TypeScript 常用的工具类型

总结了常用的工具类型

用TS保证类型安全

Awaited<Type>

获取Promise中的结果类型

ReturnType<Type>

获取函数的返回值类型. 用ReturnType

// 获取Func 类型的返回值类型
type Func = (value:string)=> string;
// 约束变量u的类型为`函数的返回值`类型
const u:ReturnType<Func> ="1";

Parameters<Type>

获取函数的参数类型,将每个参数类型放进一个元组中。 用Parametes

type U = Parameters<(a:number, b:string)=> void>;// [number, string]

NonNullable<Type>

去除类型中的null,和undefined

// 用NonNullable去除类型中的null, 和undefined类型
type U = NonNullable<string[]|null|undefined>; // string[]

Omit<Type, Keys>

省略

移除一些属性, 用Omit,Omit<T, K>从T中取出除去K的其他所有属性

本质上是Pick的反向操作,排除掉Keys。

type Test = {
  name: string;
  age: number;
  salary?: number;
};
type omitted = Omit<Test, "age">;
// 结果
// type omitted = {
//     name: string;
//     salary?: number;
// }

// 将其赋值给omitted对象
const omitted:Omitted = {
    name: 'zhangsan',
    salary:29
}

Pick<Type, Keys>

选择

从Type中选取一系列的属性, 用Pick, 构成新的类型

type Test = {
  name: string;
  age: number;
  salary?: number;
};

//pick
type Picked = Pick<Test, "name" | "age">;
// 结果
// type Picked = {
//     name: string;
//     age: number;
// }

// 将其赋值给pick对象
const pick:Picked = {
    name: 'zhangsan',
    age:29
}
type Pick<T, K extends keyof T> = {
    [P in K]: T[P]
};

Exclude<T, U>

移除

移除联合类型中的某些类型, 用Exclude<T, U>.表示从T中移除出U

type U1 = Exclude<"string"|"number"|"boolean","string">; // "number"|"boolean"

Extract<T, U>

抽取

提取联合类型中的某些类型, 用Extract<T, U>.表示从T中提取出U

type U = Extract<string | number|(()=>void), Function>; // ()=>void

Extract 提取联合类型中的函数类型,得到()=>void

1. 用于基础类型
type base1 = Extract<string | number, string>; //string || never; //实测是string
type base2 = Extract<string, string | number>; //string
2. 用于函数
type func1 = (one: number, two: string) => string;
type func2 = (one: number) => string;

//  参数少的函数类型 extends 参数多的函数类型 返回true
//  参数多的函数类型 extends 参数少的函数类型 返回false
type beginType1 = func1 extends func2 ? func1 : never; //never
type beginType2 = func2 extends func1 ? func2 : never; //func2

//这个Extract是TS内置方法
type tType1 = Extract<func1, func2>; //never
type tType2 = Extract<func2, func1>; //= (one: number) => string  和上面有区别
3.Extract 用于类
class People {
  public name!: string;
  public age!: number;
  public address!: string;
  eat() {}
}

class CnPeople extends People {
  private phone!: string;
}

let cp = new CnPeople();

// 现在这个Extractxx是自定义的,不是内置。但功效和内置的Extract一样
type Extractxx<T, U> = T extends U ? T : never;

// 定律1:子类 extends 父类; 永远true,返回T类型
type extractType = Extractxx<CnPeople, People>; // CnPeople

// 定律: 父类 extends 子类; 只有实例属性或实例方法一样时则为true
type extractType2 = Extractxx<People, CnPeople>; // never 
4. Exclude 刚好和 Extract 相反
type ec1 = Exclude<func1, func2>; //(one: number, two: string) => string;
type ec2 = Exclude<string, string | number>; //never

Partial

将类型的所有属性变为可选属性, 用Partial

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

const u:User= {  // X, 类型缺失, 报错
    name:'zhangsan'
}


const u:Partial<User> = { // 使用Partial,将所有类型变为可选后,不报错. 可赋值给变量u使用
    name:'zhangsan'
}
type Partial<T> = {
    [P in keyof T]?: T[P]
};

Required

将类型的所有属性变为必选,用Required属性

interface User{
    name?: string;
    age?: number;
    gender?: string[]

const u:Required<User> = {
    name:'zhangsan',
    age:18,
    gender:["male"]
}

Required<User>处理后的属性,直接赋值给变量u. 变量u的所有属性都是必选

type Required<T> = {
    [P in keyof T]-?: T[P]
};

Readonly

将数组或对象的属性值转换为只读的,用Readonly

interface User {
    name: string;
    age: number;
    gender?: 'male'|'female'
}
 
let u: Readonly<User> = {
   name: "hello",
   age: 10,
   gender: 'male'
}
u.age = 190   // X, 用Readonly 包裹的接口,各属性是只读的. 将其指定为变量类型.  
              // 变量赋值报错

Record

解释1: 将对象所有属性的值转化为T类型, 用Record<K extends keyof any,T>

解释2: 快速生成某种属性的K类型

解释3: Record<K,T>构造具有给定类型T的一组属性K的类型。在将一个类型的属性映射到另一个类型的属性时,Record非常方便。

解释4: 将一个类型的所有属性值都映射到另一个类型上并创造一个新的类型.

例子1:

type Property = 'use1'|'use2'
type User = Record<Property, string>

const u: User = {
    use1:'xiaoxue',
    use2:'zhangsan'
}

将生成的User类型赋值给u使用

例子2:

type HD = Record<string, string|name>
const hd:HD = {name:'zhangsan',age:28, address:'abc'}

例子3:

interface EmployeeType {
    id: number;
    fullname: string;
    role: string;
}
 
let employees: Record<number, EmployeeType> = {
    0: { id: 1, fullname: "John Doe", role: "Designer" },
    1: { id: 2, fullname: "Ibrahima Fall", role: "Developer" },
    2: { id: 3, fullname: "Sara Duckson", role: "Developer" },
}
 
// 0: { id: 1, fullname: "John Doe", role: "Designer" },
// 1: { id: 2, fullname: "Ibrahima Fall", role: "Developer" },
// 2: { id: 3, fullname: "Sara Duckson", role: "Developer" }

Record的工作方式相对简单。在这里,它期望数字作为类型,属性值的类型是EmployeeType,因此具有idfullNamerole字段的对象。

源码

/**
 * Construct a type with a set of properties K of type T
 */
type Record<K extends keyof any, T> = {
    [P in K]: T;
};

常用的格式

type proxyKType = Record<K,T>

这里会将K中的所有属性值都转换为T类型,并将返回的新类型返回给proxyKType,K可以是联合类型、对象、枚举….

//demo1
type petsGroup = 'dog' | 'cat' | 'fish';
interface IPetInfo {
    name:string,
    age:number,
}

type IPets = Record<petsGroup, IPetInfo>;

const animalsInfo:IPets = {
    dog:{
        name:'dogName',
        age:2
    },
    cat:{
        name:'catName',
        age:3
    },
    fish:{
        name:'fishName',
        age:5
    }
}

可以看到 IPets 类型是由 Record<petsGroup, IPetInfo>返回的。将petsGroup中的每个值(‘dog’ | ‘cat’ | ‘fish’)都转为 IPetInfo 类型。

当然也可以自己在第一个参数后追加额外的值,如下面:

//demo2
type petsGroup = 'dog' | 'cat' | 'fish';
interface IPetInfo {
    name:string,
    age:number,
}

type IPets = Record<petsGroup | 'otherAnamial', IPetInfo>;

const animalsInfo:IPets = {
    dog:{
        name:'dogName',
        age:2
    },
    cat:{
        name:'catName',
        age:3
    },
    fish:{
        name:'fishName',
        age:5
    },
    otherAnamial:{
        name:'otherAnamialName',
        age:10
    }
}

可以看到在demo1的基础上,demo2在

type IPets = Record<petsGroup | ‘otherAnamial’, IPetInfo>; 中除了petsGroup的值之外,还追加了 'otherAnamial’这个值。

https://www.bilibili.com/video/BV1gL411Y7Mf/?spm_id_from=333.337.search-card.all.click&vd_source=631062e9ff21033189723c8ac931c360

下一节:

手写工具类型

https://www.bilibili.com/video/BV1Lv4y1H7SK/?spm_id_from=333.337.search-card.all.click&vd_source=631062e9ff21033189723c8ac931c360

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 7
    评论
TypeScript提供了许多内置工具类,用于增强类系统的功能。其中一些常用工具类包括: 1. Partial<Type>: 将类中的所有属性都设置为可选的。这样可以方便地创建只包含部分属性的对象。 2. Required<Type>: 将类中的所有属性都设置为必需的。这样可以确保对象中的所有属性都被赋值。 3. Readonly<Type>: 将类中的所有属性都设置为只读的。这样可以防止对对象的属性进行修改。 4. Record<Key, Type>: 创建一个由指定键和值类组成的对象类。可以用于创建字典或映射类。 5. Pick<Type, Keys>: 从类中选择指定的属性。返回一个新的类,只包含指定的属性。 6. Omit<Type, Keys>: 从类中排除指定的属性。返回一个新的类,不包含指定的属性。 7. Exclude<Type, ExcludedUnion>: 从类中排除指定的联合类。返回一个新的类,不包含指定的联合类。 8. Extract<Type, Union>: 从类中提取指定的联合类。返回一个新的类,只包含指定的联合类。 9. NonNullable<Type>: 从类中排除 null 和 undefined。返回一个新的类,不包含 null 和 undefined。 10. ReturnType<Type>: 获取函数类的返回值类。 11. InstanceType<Type>: 获取构造函数类的实例类。 12. ThisType<Type>: 用于指定 this 关键字的类。可以在函数签名或对象字面量中使用,以指定 this 关键字的类为该类。 这些工具类可以帮助我们更好地定义和操作类,提高代码的可读性和可维护性。[3]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小李科技

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值