是否可以创建一个表示typeguard的类型,例如,如果您希望有一个类型来强制创建一个对象,其中键表示预期的true类型guard断言解析的typeof返回值,如下所示:

type ValueMap = {
  string: string;
  number: number;
};

type Value = ValueMap[keyof ValueMap];

您的值可以是字符串或数字.

可以创建这样的类型来判断值:

type Guards = { [K in keyof ValueMap]: (value: Value) => boolean };

但这些函数没有作为类型保护输入,我想要这样的内容:

type TypedGuards = { [K in keyof ValueMap]: (value: Value):value is K => boolean };

但这是无效的语法.

我希望该类型可以使用,以便

const guards: Guards = {
  number: (value) => true,
  string: (value) => true,
};

在一些条件陈述(例如if(guard(value)){...})中推断出正确的类型

所以基本上希望与

const typeGuards = {
  number: (value: Value): value is number => true,
  string: (value: Value): value is string => true,
};

但我想创建一个类型来表示这一点.

如果我做

const typeGuards = {
  number: (value: Value): value is number => true,
  string: (value: Value): value is string => true,
};

type TypeGuards = typeof typeGuards

我确实得到

type TypeGuards = {
    number: (value: Value) => value is number;
    string: (value: Value) => value is string;
}

但我想将其明确地表达为一个类型.

谢谢

推荐答案

你可以写

type Guards = { [K in keyof ValueMap]:
    (value: Value) => value is ValueMap[K]
};
/* type Guards = {
    string: (value: Value) => value is string;
    number: (value: Value) => value is number;
} */

您需要用index into ValueMapK来获得正确的类型(K只是"string",而不是string).

类型守护函数的类型是(value: Value) => value is string,而不是(value: Value): value is string => boolean.后者只是在语法上无效. 事实上,当您手动编写函数并查看类型时,它的形式为(value: Value) => value is string.

如果您修复了索引访问和语法拼写错误,它就会按预期工作.

Playground link to code

Typescript相关问答推荐

判断对象A中存在的对象B的键是否存在对象A中键的另一个数组值中

替换类型脚本类型中的多个特定字符串

为什么在TypScript中写入typeof someArray[number]有效?

从接口创建类型安全的嵌套 struct

参数类型undefined不能分配给参数类型字符串|未定义

泛型和数组:为什么我最终使用了`泛型T []`而不是`泛型T []`?<><>

在键和值为ARGS的泛型函数中未正确推断类型

ANGLE独立组件布线错误:没有ActivatedRouting提供程序

如何在Reaction Query Builder中添加其他字段?

如何将v-for中的迭代器编写为v-if中的字符串?

APP_INITIALIZER在继续到其他Provider 之前未解析promise

自定义 Select 组件的类型问题:使用带逗号的泛型类型<;T与不带逗号的<;T&>;时出错

使用来自API调用的JSON数据的Angular

无法缩小深度嵌套对象props 的范围

获取类属性的类型';TypeScript中的getter/setter

Typescript泛型调用对象';s方法

React Context TypeScript错误:属性';firstName';在类型';iCards|iSearch';

如何使用 AWS CDK 扩展默认 ALB 控制器策略?

Typescript 和 Rust 中跨平台的位移数字不一致

React 中如何比较两个对象数组并获取不同的值?