学习TypeScrip12(never类型)

一、never类型

  • 在TypeScript中,never类型表示一个值永远不会出现的类型。

二、它通常用于以下几种情况

2.1. 函数抛出异常

如果一个函数抛出异常,那么它的返回类型就是 never。因为在函数抛出异常后,会直接中断程序的运行,这使得程序不会继续执行到函数的返回语句那一步。

function error(message: string): never { 
  throw new Error(message); 
}

2.2. 无限循环

如果一个循环没有明确的终止条件,比如while(true),那么这个循环的返回值类型也是never,因为它永远不会自然结束。鼠标移到 infiniteLoop函数上面,可以看到函数的返回值类型为 never。

function infiniteLoop(): never { 
  while (true) { } 
}

2.3. 类型判断或类型缩小的细化(全面性检查)

在条件语句中,如果 TypeScript 能够推断出某个分支永远不会执行,那么该分支的类型会被推断为 never 。

type Value = number | string;
const processValue = (value: Value) => {
	if (typeof value === 'number') {
		// 在这个分支中,value 的类型被细化为 number
	} else if (typeof value === 'string') {
		// 在这个分支中,value 的类型被细化为 string
	} else {
		// 在这个分支中,value 的类型被细化为 never,因为 value 不可能同时为 string 和 number
		const n: never = value;
	}
};

上面的例子中,else 分支里面,value 的类型将被细化为 never 类型,然后我们将 value 赋值给一个显示声明了 never 类型的变量,如果逻辑正确,上面的代码可以正常编译通过,但如果你把 Value 的类型改成 number | string | boolean 的联合类型,此时 else 分支的 value 类型就会被细化成 boolean 类型,此时把 value 赋值给一个显示声明了 never 类型的变量就会报错。

三、 never 类型的特点

任意类型和 never 类型的联合类型都是其本身,就好比如:任意数字和0相加,都等于该数字。

type T1 = number | never;  // number
type T2 = string | never;  // string
type T3 = boolean | never; // boolean
type T4 = any | never;     // any
type T5 = unknown | never; // unknown
type T6 = never | never;   // never
type T7 = "abc" | never;   // "abc"
type T8 = 123 | never;     // 123

利用这个特点,我们可以做很多事情,比如:筛选。

我们可以利用条件类型把不符合类型 Type 的类型先转换成 never 类型,然后利用联合类型把 never 类型过滤掉,得到我们想要的结果。

type Filter<T, U> = T extends U ? T : never
type RESULT = Filter<"Echo" | 26 | true | "GuangZhou", string>

3.2. never 类型与任意类型的交叉类型都是 never

type T1 = number & never;  // never
type T2 = string & never;  // never
type T3 = boolean & never; // never
type T4 = any & never;     // never
type T5 = unknown & never; // never
type T6 = never & never;   // never
type T7 = "abc" & never;   // never
type T8 = 123 & never;     // never

3.3. never 可以赋值给任意类型

由于 never 类型是所有其他类型的子类型,所以可以将 never 赋值给任何其他类型。

let n: never
let str: string = n
let num: number = n
let b: boolean = n
let any: any = n
let unknown: unknown = n
let func: () => void = n
let symbol: symbol = n
let n1: never = n

3.4. 其他类型不能赋值给 never

由于 never 没有子类型,所以除了 never 本身,任何类型都不能赋值给 never 类型。

let n: never
n = "Echo"               // 报错:不能将类型“string”分配给类型“never”
n = 26                   // 报错:不能将类型“number”分配给类型“never”
n = true                 // 报错:不能将类型“boolean”分配给类型“never”
n = [1, 2, 3]            // 报错:不能将类型“number[]”分配给类型“never”
n = Symbol()             // 报错:不能将类型“symbol”分配给类型“never”
n = {}                   // 报错:不能将类型“{}”分配给类型“never”
n = new Array()          // 报错:不能将类型“any[]”分配给类型“never”
n = (...arg: any) => {}  // 报错:不能将类型“(...arg: any) => void”分配给类型“never”

四、never 与 void 的差异

4.1. 差异1

  • void类型表示没有返回值,但并不会出错,而never表示会抛出异常或无法执行到终止点。
//void类型只是没有返回值 但本身不会出错
function Void(): void {
	console.log();
}

//只会抛出异常没有返回值
function Never(): never {
	throw new Error('aaa');
}

3.2. 差异2

在联合类型中,never类型会被移除,因为联合类型表示至少有一个值必须满足该类型的条件,而never表示没有任何值满足条件。例如,void | number | never的类型会被推断为number。

当我们鼠标移上去的时候会发现,never在联合类型中会被直接移除

type A = void | number | never

学习TypeScrip13(symbol类型)

  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值