彻底弄懂Typescript的联合类型和交叉类型

这边笔记主要介绍TS的联合类型Union Types和交叉类型Intersection Types.(交叉类型的官网链接没找到 ),从下面4点介绍

  1. 联合类型的定义、语法
  2. 交叉类型的定义、语法
  3. 联合类型和交叉类型的异同
  4. 联合类型和交叉类型的命名缘由

联合类型 Union Types

先看下官网描述联合类型Union Types

A union type is a type formed from two or more other types, representing values that may be any one of those types. We refer to each of these types as the union’s members.

大概翻译下: 联合类型是由两个或更多其他类型构成的类型,表示可以是这些类型中的任意一个的值,我们将这些类型称为联合的成员类型。

语法: 用|连接起来多个类型。

这个特别常见,我们看个Vue源码里的例子。

type Primitive = string | number | boolean | bigint | symbol | undefined | null
type Builtin = Primitive | Function | Date | Error | RegExp

type Primitive定义了一个原始类型,只要是JS的7个原始类型之一都可以。然后定义了一个内置类型,只要是这5个Primitive | Function | Date | Error | RegExp内置类型之一都可以

疑问: 联合类型只能取其中任何一个类型吗?

联合类型只能取其中任何一个类型吗,取所有的任何类型可不可以呢,举一个例子

type Actor = {
  name: string;
  awards: string[];           // 演员获取的奖项 
  movieType: string[];        // 演员电影风格
};
type Dancer = {
  name: string;      
  danceStyle: string[];       // 舞者舞蹈风格
}

type ActorOrDancer = Actor | Dancer
const liangChaoWei: Actor = {
    name: '梁朝伟',
    awards: ['金马奖','金像奖'],
    movieType: ['战争','爱情'],
}
const yiYangQianXi: ActorOrDancer = {
    name: '易烊千玺',
    awards: ['百花奖','金像奖'],
    movieType: ['青春','校园', '战争'],
    danceStyle: ['hiphop', 'choregraphy']
}

我们定义了一个演员类型和舞者类型,还有一个联合类型,是演员或者舞者。

看到代码是完全正常的,没有任何警告,说明联合类型可以是同时包含所有的成员类型, 但是我们一般用交叉类型来表示组合类型。

交叉类型 Intersection Types

交叉类型就是用多个类型来表示一个类型,用&来连接多个类型。 举个例子。

type Actor = {
  name: string;
  awards: string[];           // List of awards the actor has won 
  movieType: string[];          // Type of movies the actor is known for
};
type Dancer = {
  name: string;      
  danceStyle: string[];  
}

type ActorOrDancer = Actor | Dancer
const liangChaoWei: Actor = {
    name: '梁朝伟',
    awards: ['金马奖','金像奖'],
    movieType: ['战争','古装'],
}
const yiYangQianXi: ActorOrDancer = {
    name: '易烊千玺',
    awards: ['百花奖','金像奖'],
    movieType: ['青春','爱情'],
    danceStyle: ['hiphop', 'choregraphy'], // Style of dance the dancer is known for
}

type Versatile = Actor & Dancer
const wangYiBo: Versatile = {
    name: '王一博',
    awards: ['华鼎奖','金鹰奖'],
    movieType: ['悬疑','剧情'],
    danceStyle: ['hiphop', 'choregraphy'], // Style of dance the dancer is known for
}

// 这个会提示缺少演员的属性
const x: Versatile = {
    name: '张三',
    danceStyle: ['jazz'];  
}

我们定义了多才多艺类型Versatile,既有演员的才能又有舞蹈的才能

截图我们定义了一个X,只有舞者类型,就会提示缺少演员属性。看下实际代码例子,Vue源码里的h.ts文件, 渲染虚拟dom的h函数。

export function h<P>(
  type: string | Component<P>,
  props?: (RawProps & P) | ({} extends P ? null : never),
  children?: RawChildren | RawSlots,
): VNode

我们看到props, (RawProps & P),就是既有RawProps,又有传过来的P.

联合类型和交叉类型的异同

共同点: 都是用多个类型来组成自己类型,当联合类型是表示成员里的所有类型时,它和交叉类型表示的就是完全一样的。

不同点: 交叉类型一定要成员类型的所有类型,不可以是任意一个。而联合类型可以是任意一个成员类型,也可以是所有的。

面试被问到的时候,交叉类型,当时就以为是多个类型的共同部分,现在知道了是把多个类型合并起来,那为什么要叫交叉类型呢?

联合类型和交叉类型的命名缘由

联合类型就是就是取集合成员的联合,包括集合成员本身和交集,也就是数学里面的并集,这也就是为什么联合类型取任意类型或包含的所有类型都可以,也可以理解为什么叫联合类型,就是集合的并集。

同理:交叉类型, 把组成的每个类型看成一个集合,取集合的交集,所以要同时满足所有的组成类型,而不是所有的组成类型共同部分,这样也就明白了为什么要叫交叉类型,原来和数学的集合有关。

  • 4
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值