对非数组类型使用 typeof
类型保护非常简单(示例来自 docs ):
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}'.`); }
但是,当涉及到数组类型时,它会变得更加复杂。 我假设以下代码可以工作:
function join(array: number[] | string[]): string {
if (typeof array[0] === 'number') {
return foo(array);
} else {
return bar(array)
}
}
function foo(n: number[]): string {
return n.join();
}
function bar(s: string[]): string {
return s.join();
}
对我来说似乎很简单:预期类型是数字数组或字符串数组。
如果数组中第一个元素的类型是 number
,则数组的类型是 number[]
。否则,这是一个字符串数组。
不幸的是,TypeScript 编译器不是那么聪明,我得到了一个编译错误:
Argument of type 'number[] | string[]' is not assignable to parameter of type 'string[]'
如何让它发挥作用?
最佳答案
答案是用户定义的类型保护。
您可以定义自己的类型保护来确定数组是否为数字数组:
function isNumbers(array: number[] | string[]): array is number[] {
return typeof array[0] === 'number'
}
阅读更多关于用户定义类型保护的信息 here .
以下是您的代码的工作示例:
function join(array: number[] | string[]): string {
if (isNumbers(array)) {
return foo(array);
} else {
return bar(array)
}
}
function foo(n: number[]): string {
return n.join();
}
function bar(s: string[]): string {
return s.join();
}
function isNumbers(array: number[] | string[]): array is number[] {
return typeof array[0] === 'number'
}
TypeScript Playground example .
关于arrays - 数组类型的类型保护,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49813443/