泛型-
大约 1 分钟
泛型函数
定义泛型函数,,此函数有个类型变量 T,T可以帮助我们捕获用户传入的类型
function getType<T>(type: T) {
return type
}
调用泛型函数
//type 是number类型
getType<number>(1)
//不用 <> 时,type 就是字面量类型 123
getType("123")
泛型约束
如果我们想在函数里面获取 type
的 length
属性,但是编译器并不能确定type
上一定有 length
属性,所以编译器会报错:
//Property length does not exist on type T
type.length
我们可以使用 typeof
关键字进行类型收缩
function getType<T>(type: T) {
if (typeof type === "string") {
type.substring(1)
} else if (typeof type === "number") {
type.toFixed(0)
}
return type
}
我们还可以定义一个接口,创建一个包含 length
属性的接口,使用 extends
关键字来实现约束。如果传入的参数没有 length
属性,(如数字100),编译器则会报错。
interface ILength{
length:number
}
function getLength<T extends ILength>(type:T){
console.log(type.length)
}
getLength('abc')
getLength([1,3])
//Error: Argument of type number is not assignable to parameter of type ILength
getLength(100)
泛型中使用 keyof
我们需要在下面这个泛型函数中用属性名从对象中获取这个属性值,如果直接使用 **obj[key]**的话会报错,因为编译器并不能确定这个对象上面一定会有key这个属性。
function getKey<O,K>(obj:O,key:K){
//Error: Type K cannot be used to index type O
console.log(obj[key])
}
我们可以使用 keyof
关键字对 K
进行约束
//keyof O 可以理解为 O 的所有属性
function getKey<O,K extends keyof O>(obj:O,key:K){
return obj[key]
}
const user={
name:'rice',
age:18
}
getKey(user,'name') //rice
//Error: Argument of type "gender" is not assignable to parameter of type "name" | "age"
getKey(user,'gender')
泛型接口
interface IUser<T>{
id:T,
name:string
}
const userInfo:IUser<number>={
id:1,
name:'rice'
}