泛型的作用
- 泛型是一种特殊的变量,
只用来表示类型而不是值
- 它用来创建可重用的组件
应该在什么时候使用泛型
- 以一个函数为例
- 如果不确定传入和传出的是否为统一数据类型时,就可以使用泛型来统一定义
- 如果知道这个参数具有某种方法,但是具有这个方法的类型又不止一个时,也可以使用泛型来统一定义,之后再对它稍作约束
使用泛型
泛型变量
因为泛型是任意类型,所以使用的如果不是所有类型的公共属性或这方法,便会报错
泛型的声名
泛型函数
function 方法名<T>
泛型数组
Array<T>
泛型接口
interface 接口名<T>
- 用泛型定义接口的话,必须再使用时传入一个类型参数来指定泛型类型,锁定之后代码里使用的类型
1
2
3
4
5
6
7
8
9interface GenericIdentityFn<T> {
(arg: T): T;
}
function identity<T>(arg: T): T {
return arg;
}
let myIdentity: GenericIdentityFn<number> = identity;
- 用泛型定义接口的话,必须再使用时传入一个类型参数来指定泛型类型,锁定之后代码里使用的类型
泛型类
class 类名<T>
- 泛型类指的是
实例部分
的类型,所以类的静态属性不能使用这个泛型类型
- 泛型类指的是
泛型约束
约束是什么?
虽然泛型变量是任意类型的,但是我们可以在让它不那么任意
,也就是有限制条件的类型
如何约束泛型
比如说,成为我的(T)必须是具有length属性的类型,且length属性的值为number类型(
<T extends Lengthwise>
)1
2
3
4
5
6
7
8interface Lengthwise {
length: number;
}
function loggingIdentity<T extends Lengthwise>(arg: T): T {
console.log(arg.length);
return arg;
}也可以直接使用类型参数来进行泛型约束
1
2
3
4
5
6
7
8function getProperty(obj: T, key: K) {
return obj[key];
}
let x = { a: 1, b: 2, c: 3, d: 4 };
getProperty(x, "a"); // okay
getProperty(x, "m"); // error: Argument of type 'm' isn't assignable to 'a' | 'b' | 'c' | 'd'.