【问题标题】:Why does keyof yield a union of properties rather than an intersection of properties?为什么 keyof 产生属性的并集而不是属性的交集?
【发布时间】:2019-09-10 18:51:50
【问题描述】:

keyof 与以下类型一起使用会产生属性名称的union

type Person = {
    name: string;
    age: number;
    location: string;
}

type K1 = keyof Person; // "name" | "age" | "location"

同样,如果我使用利用ExcludeOmit 助手,我必须为keyof T 提供union 的属性,直观地我会期望提供@987654328 @ of properties 要省略,但事实并非如此:

type Omit<T, K extends keyof T> = Pick<T, Exclude<keyof T, K>>;
type PersonName = Omit<Person, "location" | "age">;  
// type Person = { name: string }

根据我的理解,我认为应该是 type 的组合,因为它需要所有属性的 intersection 而不是属性的 union

// This isn't valid, but what I'd expect using keyof
type K1 = keyof Person; // "name" & "age" & "location"
type PersonName = Omit<Person, "location" & "age">;

当谈到keyof 时,我对作为union 而不是intersection 的属性键的type 产生的属性的理解在哪里? type 不能像union 所描述的那样,每个属性都是 either 场景。 type 无效,除非它是所有 properties 中的 intersection 正确吗?

【问题讨论】:

    标签: typescript


    【解决方案1】:

    如果每个属性都是联合所描述的两种情况,则该类型不能存在。

    keyof T 没有描述类型T,它描述了一种可能的键类型,可用于获取T 的属性,即表达式key 变量t[key] 中的类型,其中t 值的类型为 T。毕竟,这是 javascript 的类型系统,其中属性访问t.propertyName 与稍微详细一点的t["propertyName"] 完全相同,后者始终允许使用包含属性名称的变量动态访问对象属性。

    这是一个联合类型,因为您可以在 t[key] 表达式中使用任何单个键。

    文字类型的交集是没有意义的——类型"name" &amp; "age" &amp; "location"意味着一个变量值同时等于所有三个文字值,这是不可能的。在内部,这样的交叉点被简化为never 类型。

    【讨论】:

    • type "name" &amp; "age" &amp; "location" means that a variable value is equal to all three literal values at the same time, which is impossible 非常适合帮我解决这个问题,谢谢。我知道我的理解错了。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-05-08
    • 2014-06-27
    • 2019-11-22
    • 2016-06-22
    • 2011-07-23
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多