一、什么是泛型
二、接口和抽象类的区别
- 不同类之间的公有的属性或者方法,可以抽象成一个接口(interface)。
- 抽象类是提供一个基础类供其他类继承,抽象类不能被实例化。抽象类中的方法必须在子类中实现。
- 一个类可以继承一个抽象类或者类(extends),但可以实现多个接口(implements)。
-
三、接口和类型别名的区别
类型别名不能被继承(extends)和实现(implements),如果一个类型需要被继承或者实现的话要用接口的形式。
- 当我们需要使用联合类型后者元组的时候,类型别名更合适。
四、typeof、keyof、ReturnType、infer、InstanceType的用途
1、typeof操作符
在typescript中typeof关键字可以获取一个变量或者对象的类型。
typeof操作符出了可以获取对象的结构类型之外,还可以获取函数对象的类型。interface Person {name: string,age: number}const sum: Person = { name: 'wz', age: 18 };type Sum = typeof sum; // type Sum = Person
function toArray(x: number): Array<number> {return [x];}type Func = typeof toArray; // (x: number) => number[]
2、keyof操作符
在typescript中keyof关键字用来查询索引类型的操作符。
在自定义的时候可以用in操作符去批量定义类型中的属性。interface Person {name: string,age: number}type PersonKey = keyof Person; // type PersonKey = name | age
interface Person {name: string,age: number}type PartPerson = { // 该方法将一个接口中的属性都变成可选属性[Key in keyof Person]?: Person[key]}
3、ReturnType操作符
在typescript中ReturnType关键字是用来获取函数的返回类型的操作符。
infer关键字表示在extends条件语句中待推断的类型变量。
可以通ReturnType的方式获取函数返回值的类型。
下方是ReturnType的实现方式:const getUserInfor = () => ({ name: 'wz', age: 18 });type UserInfo = ReturnType<typeof getUserInfo>;const user: UserInfo = { name: 'wz', age: 18 };// 实质上UserInfo的类型可以推断到的类型为:interface UserInfo {name: string,age: number}
type ReturnType<T extends (...args: any[]) => any>= T extends (...args: any[]) => infer R ? R : any;
4、InstanceType操作符
在typescript中InstanceType获取构造函数类型的实例类型。使用方式为InstanceType,可以获取通过构造函数创建出的对象的类型。下方是实现方式: type Construtor = new (...args: any[]) => any;type ConstrutorParams<T extends Construtor> = T extends new (...args: infer P) => any ? P : any;type InstanceType<T extends Construtor> = T extends new (...args: any[]) => infer R ? R : any;class Person {name: stringconstrutor(name) {this.name = name;}getName() {return this.name;}}// 获取构造函数的参数type constructorParams = ConstrutorParams<typeof Person>;type Instance = InstanceType<Person>;const instance: Instance = { name: 'wz', getName() {} };
五、Exclude、Extract、NonNullable的用途以及实现
1、Exclude关键字
在typescript中Exclude关键字是用来从一个T类型中剔除U类型的。从T可分配的类型中排除U。type E = Exclude<string | number, string>;const e: E = 10; // E: number// 以下为实现过程type Exclude = T extends U ? never : T;
2、Extract关键字
在typescript中Extract关键字是用来从一个T类型中拿到U类型的。从T可分配的类型中提取U。type E = Extract<string | number, string>;const e: E = 'wz'; // E: string// 以下为实现过程type Extract = T extends U ? T : never;
3、NonNullable关键字
在typescript中NonNullable关键字是用来从一个T类型中排除null和undefined。type E = NonNullable<string | number | null | undefined>;const e: E = 10 // E: string | number// 以下是实现过程type NonNullable = T extends null | undefined ? never : T;
六、Partial、Required、ReadOnly、Pick、Record、Omit的用途以及实现
1、Partial关键字
在typescript中Partial关键字可以用来将传入的属性变成可选的。interface Person {name: string,age: number}type person = Partial<Person>;const a: person = {}; // 正确不会报错// 以下是实现方式type Partial<T> = { [P in keyof T]?: T[P] };
2、Required关键字
在typescript中Required关键字可以将传入的属性中的可选项变成必选项,这里用-?修饰符来实现。interface Person {name: string,age: number}const p: Required<Person> = { name: 'wz' };// 以下是实现方式type Required<T> = { [P in keyof T]-?: T[P] };
3、ReadOnly关键字
在typescript中ReadOnly关键字可以将传入的属性都加上readonly修饰符。// 以下是实现方式type ReadOnly<T> = { readonly [P in keyof T]: T[P] };
4、Pick关键字
在typescript中Pick关键字可以帮助我们从传入的属性集合中摘取某一项返回。interface Person {name: string,age: number}type person = Pick<Person, 'name'> // person = { name: string }// 以下是实现方法type Pick<T, K extends keyof T> = { [P in K]: T[P] };
5、Record关键字
在typescript中Record关键字可以将一个类型的所有属性映射到另一个类型,并返回一个新的类型。interface Person {name: string,age: number}type p = Record<string | number, Person> // p = { [x: string]: Person, [x: number]: Person };// 以下是实现方法type Record<K extends keyof any, T> = { [P in K]: T };
6、Omit关键字
在typescript中Omit关键字可以帮助我们排除传入属性集合中的某些属性。interface Person {name: stringage: numberid: number}type p = Omit<Person, 'age'> // p = { name: string, id: number }// 以下是实现方法type Omit<T, K extends keyof any> = Pick<T, Exclude<keyof K, T>>;
