数组类型的Type Guards实现难点:对比非数组typeof类型守卫的简易实现
用typeof类型守卫处理数组类型的那些坑
咱们都知道,用typeof类型守卫处理字符串、数字这类基础类型特别顺手,就像官方文档里的这个例子:
function padLeft(value: string, padding: string | number) { if (typeof padding === "number") { return Array(padding + 1).join(" ") + value; } if (typeof padding === "string") { return padding + value; } throw new Error(`Expected string or number, got '${padding}'.`); }
判断padding是数字还是字符串,逻辑清晰得很。
但轮到处理数组类型的时候,事儿就没这么简单了。我之前天真地以为写个类似的逻辑就能跑通,比如想写个join函数拼接数组元素,一开始写的代码大概是这样:
// 我最初的错误尝试 function join(arr: string[] | number[], separator: string) { if (typeof arr === "array") { // 这里会报错! return arr.join(separator); } throw new Error("Expected an array"); }
结果一运行就傻了——typeof判断数组的时候返回的是"object",根本不是"array"!这时候typeof就不好使了,得换别的方法。
那该怎么正确判断数组类型呢?给你俩靠谱的方案:
方案一:用
Array.isArray()
这是最直接的方法,TypeScript能识别这个类型守卫:function join(arr: string[] | number[], separator: string) { if (Array.isArray(arr)) { return arr.join(separator); } throw new Error("Expected an array"); }方案二:用instanceof(仅限浏览器/Node环境)
如果你的代码运行在有全局Array构造函数的环境里,也可以这么写:function join(arr: string[] | number[], separator: string) { if (arr instanceof Array) { return arr.join(separator); } throw new Error("Expected an array"); }
为啥typeof对数组不管用?因为在JavaScript里,数组本质上就是一种特殊的对象,所以typeof []返回的是"object",这是语言本身的特性,TypeScript也得跟着这个规则来。
内容的提问来源于stack exchange,提问作者JeB
相关产品推荐
相关产品推荐

