1、概念
泛型(Generics)是指在定义接口、函数等类型的时候,不预先指定具体的类型,而在使用的时候再指定类型的一种特性, 使用泛型可以复用类型并且让类型更加灵活。
2、泛型接口
语法:在接口类型的名称后面使用<T>
即可声明一个泛型参数列表,接口里的其他成员都能使用该参数的类型。
通用思路:
- 找到可变的类型部分通过泛型抽象为泛型参数(定义参数)
泛型参数相当于一个类型容器,能够捕获用户提供的类型(具体是什么类型由用户调用该函数时指定)
- 在使用泛型的时候,把具体类型传入到泛型参数位置 (传参)
interface UserInfo {
code: number;
msg: string;
data: {
name: string;
age: number;
};
}
interface GoodsInfo {
code: number;
msg: string;
data: {
id: number;
goodsName: string;
}[];
}
interface Res<T2> {
code: number,
msg: string,
data: T2
}
type User = { name: string, age: number }
// 请求得到用户信息
const res1: Res<User> = { code: 200, msg: 'success', data: { name: 'jack', age: 18 } }
// 请求得到商品信息
const res2: Res<{ goodsName: string, id: number }[]> = { code: 200, msg: 'success', data: [{ id: 1001, goodsName: '衬衣' }] }
3、泛型-类型别名
语法:在类型别名type的后面使用<T>
即可声明一个泛型参数,接口里的其他成员都能使用该参数的类型
const res1:UserInfo = {code: 200, msg: 'success', data: {name: 'jack', age: 18}}
const res2 = {code: 200, msg: 'success', data: [{id: 1001, goodsName: '衬衣'}]}
type Res<T> = {
code:number,
msg:string,
data:T
}
type User = { name:string, age:number }
type UserInfo = Res<User>
4、泛型-函数:
语法:在函数名称的后面使用<T>即可声明泛型参数,整个函数中(参数、返回值、函数体)的变量都可以使用该参数的类型
function createArray<T>(len:number, initValue:T): T[] {
let result:T[] = [];
for (let i = 0; i < length; i++) {
result[i] = initValue
}
return result
}
createArray(4,'a') // 得到一个长度为4的数组,它的每个元素都是'a'
createArray(3,1) // 得到一个长度为3的数组,它的每个元素都是1
5、泛型约束:
作用:泛型的特点就是灵活不确定,有些时候泛型函数的内部需要访问一些特定类型的数据才有的属性,此时会有类型错误,需要通过泛型约束解决