TypeScript - interface 和 type 的区别

前言

本文主要记录下 TypeScript 中接口(interface) 和类型别名(type) 的区别,日常学习总结篇。 

一、 基本概念

1⃣️、接口 interface

在 TypeScript 里,接口的作用就是为这些类型命名和为你的代码或第三方代码定义契约,接口除了能描述对象外,还能描述函数与事件。示例如下:

interface IPerson {
  name: string
  age: number
}

const user: IPerson = {
  name: 'Jenny',
  age: 18
}

2⃣️、类型别名 type

类型别名会给一个类型起个新名字。类型别名有时和接口很像,但是可以作用于原始值,联合类型,元组以及其它任何你需要手写的类型。示例如下:

type Person = {
  name: string
  age: number
}

const user: Person = {
  name: 'Jenny',
  age: 18
}
二、相同点

1⃣️、都可以描述一个对象或者函数。

// 接口 interface
interface Person {
  name: string
  age: number
}

interface SetPerson {
  (name: string, age: number): void
}

// 类型别名 type
type Person = {
  name: string
  age: number
}

type SetPerson = (name: string, age: number) => void

2⃣️、都可以扩展

interface 和 type 可以混合扩展,也就是说 interface 可以扩展 type,type 也可以扩展interface。但是,接口的扩展是继承(extends)。类型别名的扩展是交叉类型(通过 & 实现)。示例如下:

a. interface 继承 interface

interface Person {
  name: string
}

interface User extends Person {
  age: number
}

const student: User =  {
  name: 'Jenny',
  age: 18
}

b. type 继承 type

type Person = {
  name: string
}

type User = Person & { age: number }

const student: User =  {
  name: 'Jenny',
  age: 18
}

c. interface 继承 type

type Person = {
  name: string
}

interface User extends Person {
  age: number
}

const student: User =  {
  name: 'Jenny',
  age: 18
}

d. type 继承 interface

interface Person {
  name: string
}

type User = Person & { age: number }

const student: User =  {
  name: 'Jenny',
  age: 18
}
三、不同点

1⃣️、type 可以,interface 不行

a. interface 只能定义对象类型或者函数事件等;type 可以声明任何类型,包括基础类型、联合类型(A | B)、交叉类型(A & B)、元组等。

// 基础类型
type Name = string

// 联合类型
type Value = number | string | boolean

// 交叉类型
type Person = {
  name: string
}
type User = Person & { age: number }

// 元组类型
type List = [number, string]

b. type 中可以使用 in *** 作符进行映射类型。

type keys = 'a' | 'b' | 'c'
 
type obj = {
  [p in keys]: any
} // { a: any, b: any, c: any}

c. type 语句中还可以使用 typeof 获取实例的类型进行赋值。

// 当获取一个变量的类型时,使用 typeof
let div = document.createElement('div')

type B = typeof div // HTMLDivElement

2⃣️、interface 可以,type 不行

interface 支持声明合并,type 不支持。

interface Person {
  name: string
}
interface Person {
  age: number
}
// 重复声明 interface,就合并了,相当于:
// interface Person {
//   name: string
//   age: number
// }

const user: Person = {
  name: 'Jenny',
  age: 18
}
type Person = {
  name: string
}
// 报错:标识符 “Person” 重复。
type Person = {
  age: number
}
四、总结

在不确定使用 type / interface 时,建议优先选择 interface,若 interface 满足不了再使用 type。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/web/925222.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-16
下一篇 2022-05-16

发表评论

登录后才能评论

评论列表(0条)

保存