Ada*_*son 5 typescript typescript-generics typescript-typings
我有一个例子,我经常一起检查布尔值和另一个联合类型的值。虽然它们在逻辑上是相连的,并且假设可以只检查其中之一,但我需要检查两者,以便 TS 编译器知道这两种类型。
let multiple: boolean
let value: Array<string> | string
...
if (multiple && isArray(value)) {
// TS knows multiple === true and value is an Array
}
Run Code Online (Sandbox Code Playgroud)
有没有办法编写类型检查函数,其中类型谓词断言多个值?
像这样的东西:
// Not valid Typescript
function isMulti (
multi: boolean,
value: Array<string> | string
): (multi is true) && (value is Array<string>) {
return multi && isArray(value)
}
Run Code Online (Sandbox Code Playgroud)
在大多数情况下,我只需检查即可isArray,但有些情况下我想重复使用上面的检查。这可能吗?
回复@kaya3:
为了给出更准确的用例,我有类似以下内容:
我可以将multiple和分配value给具有 DiscriminatedUnion 类型的对象,但这会增加比我认为需要的更多的复杂性。
type ValueType<M extends boolean> = M extends true ? Array<string> : string;
interface PropTypes<M extends boolean> {
multiple: M,
// more properties
}
type DiscriminatedUnion = {
multiple: true,
value: Array<string>
} | {
multiple: false,
value: string
}
function myFunction<M extends boolean>({
multiple
}: PropTypes<M>) {
let value: ValueType<M>;
// ... later
if (multiple) {
// TS will not assert the type of `value` here
}
// Trying discriminated union
// TS Error: Type '{ multiple: boolean; value: string | string[]; }' is not assignable to type '{ multiple: false; value: string; }'
let obj: DiscriminatedUnion = {
multiple,
value
}
}
Run Code Online (Sandbox Code Playgroud)
目前无法通过这种方式解决您的问题;@jcalz 很有帮助地指出,有一个开放的功能请求。也就是说,您的问题可能可以通过不同的方式得到更好的解决。
对于几乎任何问题,比如“我有这两个值,我如何告诉 Typescript 它们的类型是相关的?”,答案是将它们作为属性放在一个对象中。然后,您可以将对象的类型设置为可区分联合,以便对其中一个属性进行测试可以缩小整个对象的类型范围。
type DiscriminatedUnion =
| {multiple: false, value: string}
| {multiple: true, value: string[]}
declare let obj: DiscriminatedUnion;
if(obj.multiple) {
// here, obj.value is narrowed to string[]
obj.value
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
2299 次 |
| 最近记录: |