TypeScript 中的 type 和 interface 的区别与异同
在 TypeScript 中,type 和 interface 就像是两个截然不同的角色:
type 是一个多面手,可以扮演各种类型的角色
interface 则是一个专业的“对象设计师”,专注于定义对象的外貌和行为。
让我们更简洁、深入了解他们的区别吧!
一、type 和 interface 的定义
type
-
type alias(类型别名):type 关键字用于声明一个新的类型别名。它可以用来给现有类型起一个新名称,也可以用来创建复合类型、联合类型、元组类型、字面量类型等。type 使用等号来定义类型别名。
// 类型别名示例 type StringNumber = string | number; // 创建一个可以是字符串或数字的联合类型 type PersonInfo = { name: string; age: number; }; // 定义一个表示人信息的对象类型
interface
-
接口(Interface):interface 关键字用于定义对象结构形状的一个蓝图,它描述了对象必须具有的属性和方法签名。接口可以被类实现,也可以用作类型注解来约束变量、函数参数和返回值的形状。而 interface 使用花括号直接定义接口的成员。
// 接口定义示例 interface IPerson { name: string; age: number; } // 类实现接口示例 class Person implements IPerson { name: string; age: number; constructor(name: string, age: number) { this.name = name; this.age = age; } }
二、区别与共同点
- 相同点:
- type 和 interface 都可以用来定义对象类型,并且在描述简单对象结构时,二者的行为几乎一致
- 它们都可以扩展其他类型或者接口,并能够合并(在 TypeScript 2.8 及更高版本中,通过声明合并机制)。
- 不同点:
-
type 更为灵活,可以定义更复杂的类型表达式,如上述提到的联合类型、元组类型等。
-
在声明合并上,interface 默认支持extends多重继承和合并,而 type 除了别名外,在定义对象类型时不支持合并,但可以通过使用 & 操作符手动实现类似效果。
请添加图片描述
type 适合于定义复杂的类型别名和泛型类型,以及进行条件类型的定义。interface 也具有相似的能力,它适合于描述对象的形状,定义类的契约和实现,以及接口之间的继承和扩展。
- 从工程角度,type 声明更适合于内部逻辑的抽象,而 interface 更多地用于公共契约(API 约定)的设计和实现上的约束。
- 从历史版本兼容性来看,早期的 TypeScript 版本中,只有 interface 支持泛型,但现在两者都支持泛型。
三、type 和 interface 的兼容性
-
type:如果对类型别名进行重复定义,TypeScript 会报错。这意味着不能重新定义一个已存在的 type
type A = { x: string }; type A = { y: string }; // 错误: 重复定义
-
interface:如果定义了多个同名的接口,它们会被合并成一个单一的接口,而不是报错。当多个同名接口出现时,它们的成员会被合并为一个接口,这种合并会在类型级别上进行,不会在运行时产生影响。合并机制使得 TypeScript 中的接口能够更加灵活地进行组织和管理
interface A { x: string; } interface A { y: string; z: string; } // A 的成员被合并为 { x: string; y: string; z: string }
END
在日常开发工作中,我们要遵循团队规范。例如,可以用 interface 定义一个复杂的对象类型,在组合不同类型时,可以使用 type 关键字来定义