【问题标题】:all possible keys of an union type联合类型的所有可能键
【发布时间】:2018-08-30 07:25:24
【问题描述】:

我想获取联合类型的所有可用键。

interface Foo {
  foo: string;
}

interface Bar {
   bar: string;
}

type Batz = Foo | Bar;

type AvailableKeys = keyof Batz;

我想要'foo' | 'bar' 作为AvailableKeys 的结果,但它是never(作为替代我可以做keyof (Foo & Bar),它会产生确切所需的类型,但我想避免重复这些类型)。

我已经在 github 上找到了问题 keyof union type should produce union of keys。我理解答案,keyof UnionType 不应该产生所有可能的密钥。

所以我的问题是:是否有其他方法可以获取所有可能键的列表(如果需要 tsc 的 2.8 版本也可以)?

【问题讨论】:

    标签: typescript


    【解决方案1】:

    你需要一个交集类型,而不是联合类型:

    type Batz = Foo & Bar;
    

    我同意它们的命名有时会令人困惑。

    【讨论】:

    • 感谢您的回答,但我真正的意思是联合类型。我想获取联合类型的所有可能键(是 Foo 或 Bar),以便我可以进行详尽的检查。
    • @Xenya 您能否提供一个type Batz = Foo & Bar; 无法获取密钥的案例?在上述情况下,Batz 符合预期的是'foo' | 'bar'
    • 你是对的,因为得到了它的工作原理。但我已经有了type Batz = Foo | Bar; 类型。我想避免用&重写类型。
    【解决方案2】:

    这可以在 typescript 2.8 及更高版本中使用条件类型来完成。条件类型迭代联合中的类型,合并结果:

    type Batz = Foo | Bar;
    
    type KeysOfUnion<T> = T extends T ? keyof T: never;
    // AvailableKeys will basically be keyof Foo | keyof Bar 
    // so it will be  "foo" | "bar"
    type AvailableKeys = KeysOfUnion<Batz>; 
    

    一个简单的keyof Union 不起作用的原因是keyof 总是返回一个类型的可访问键,在联合的情况下,它只会是公共键。 KeysOfUnion 中的条件类型实际上会获取联合中的每个成员并获取其键,因此结果将是 keyof 的联合应用于联合中的每个成员。

    【讨论】:

    • 这太棒了——你能解释一下 KeysOfUnion 类型和简单的 keyof T 类型之间的区别吗?前者返回键的正确联合,后者返回一个交集(没用)
    • @dmwong2268 添加了更多解释,让我知道是否清楚
    • @TitianCernicova-Dragomir 您的解决方案有效,但您的解释似乎没有解释任何内容,只是重新说明了行为。我发现了一个关于 gitter 的讨论,您在其中指出了解释它的正确位置,所以让我在这里添加它:typescriptlang.org/docs/handbook/…
    • 很好的答案!我还发现你必须使用泛型,否则它不起作用。 type allBatzKeys = KeysOfUnion // "foo"|"bar" type alternativeAllBatzKeys = Batz extends any ?巴茨的关键:从不; // 从不
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-08-18
    • 2010-12-29
    • 1970-01-01
    • 1970-01-01
    • 2017-05-31
    • 1970-01-01
    相关资源
    最近更新 更多