typescript之泛型

222 阅读1分钟

说明

在定义类型的时候,固定的类型输出有时候不能满足我们的需求,为了接口的设计更加灵活,ts提供了类似于函数传参的方式让我们可以通过指定输入来定制化的输出不同的接口定义,这种输入的'参数'类型称之为泛型

简单的例子

interface Person<T>{
  name:string;
  like:T;
}

const xiaomin:Person<number> = {
  name:'xiaomin',
  //like:'11', //报错
  like:11
}

通过上面的例子可以看出,Person类型的like属性的类型取决于传入的T类型

函数中使用泛型

function person<T>(name: T): T {
  return name
}
person<number>('xiaoming') //报错
person<string>('xiaoming')

与接口的泛型使用一样,在应用类型的时候传入的泛型类型,决定了最终的函数类型,当T是number类型的时候,传入的参数必须是number类型,否则报错

class中使用泛型

class Person<T>{
  public personName: T

  setPersonName(name: T) {
    this.personName = name
  }
}

const person = new Person<string>()
person.setPersonName(11) //报错
person.setPersonName('111') // pass

多个泛型参数

class Person<T, U> {
  public personName: T
  public age: U

  setPersonName(name: T) {
    this.personName = name
  }
  setAge(age: U) {
    this.age = age
  }
}

const person = new Person<string, number>()
// person.setPersonName(11) //报错
person.setPersonName('111') // pass

// person.setPersonName('18') //报错
person.setAge(18) // pass

泛型约束

可以通过extends来约束传入的类型,例如:

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

function createPerson<T extends BaseInter>(person: T): T {
  return person
}

interface Xiaohong {
  name: string;
  age: number;
  count: number;
}


createPerson<string>() //报错
createPerson<Xiaohong>({ name: 'xiaohong', age: 18, count:1 })

上面的例子可以看到createPerson传入的泛型类型必须要满足BaseInter否则就会报错