Interface
Interface可以使用extends
和implements
。它在声明的那一刻并不是最终类型,由于interface可以进行声明合并,在创建后是可变的,可以将新成员添加到同一个interface中。
Type
可以声明基本类型别名,联合类型,元组等类型。类型别名不会创建类型,它只是创建了一个新名字来引用那个类型,其实就是一个对象字面量类型,所以类型别名一旦声明就无法更改它们
Interface 与 Type 定义对象
type Father = {
name:string;
age: number;
work: () => string;
};
interface Son {
name: string;
age: number;
work: () => string;
}
// 类型别名对象
const f: Father = { name: "张三", age: 33, work: () => "程序员" };
// 接口对象
const s: Son = { name: "小三", age: 12, work: () => "学生" };
Interface 与 Type 定义函数
type FatherFn = (name: string) => string;
interface SonFn {
(name: string): string;
}
// 类型别名函数
const fn: FatherFn = (name:string): string => name
// 接口函数
const sn: SonFn = (name:string): string => name
Interface 扩展
通过extends
和 implements
扩展
interface Person {
name: string;
}
interface User extends Person {
age: number;
}
class Child implements User {
name: string;
age: number;
constructor(name: string, age: number) {
this.name = name;
this.age = age;
}
}
const u1: User = { name: "张三", age: 18 };
const u2: User = new Child("张三", 18);
Type 扩展
通过交叉类型&实现扩展
type Person = {
name: string;
};
// type交叉类型
type User = Person & { age: number };
class Child {
name: string;
age: number;
constructor(name: string, age: number) {
this.name = name;
this.age = age;
}
}
const u1: User = { name: "张三", age: 18 };
const u2: User = new Child("张三", 18);
接口的声明合并
多次声明同一个同名接口,TS会将它们合并到一个接口中,而type则会报错
interface Person {
name: string;
}
interface Person {
age: number;
}
let user: Person = { name: "张三", age: 18 };
Type 定义字符串字面量联合类型
type Person = "left" | "right" | "top" | "bottom";
//这里user只能写"left" | "right" | "top" | "bottom",否则会报错
let user: Person = "left";
type Value = string | number | boolean;
// 这里num只能是数字,字符串,布尔值
let num: Value = 18;
Type 定义元组类型
每个位置的类型必须一样
interface Person {
name: string;
}
type User = {
age: number;
};
type Child = [Person, User];
const user: Child = [{ name: "张三" }, { age: 18 }];
Interface extends Type
type Person = {
name: string;
};
interface User extends Person {
age: number;
}
Type 与 Interface 交叉类型
interface Person {
name: string;
}
type User = Person & {
age: number;
};
最后,几乎所有interface具有的功能,type都可以实现,主要区别在于type不能重新打开类型来添加新成员,而接口总是可以扩展的,即便这样官方还是建议我们尽量去使用接口代替类型别名。另一方面,如果你无法通过接口来描述一个类型并且需要使用联合类型或元组类型,这时通常会使用类型别名。