[英]How to Infer Generic Property Types?
我不知道如何根据它所在对象的泛型类型来推断泛型属性的类型。 在下面的例子中,我怎么能说Something.aProp
需要匹配Something 的U.obj.prop
的类型?
interface Prop {
a: number;
}
interface FancyProp extends Prop {
b: number;
}
interface Obj<T extends Prop> {
prop: T;
}
interface FancyObj extends Obj<FancyProp> {}
interface Parent<T extends Obj<any>> { // <-- the <any> here seems wrong too
obj: T;
}
interface FancyParent extends Parent<FancyObj> {
fancy: number;
}
class Something<U extends Parent<any>> {
aProp: typeof U.obj.prop;
}
即Something<Parent>.aProp
应该是Prop
类型,而Something<FancyParent>.aProp
是FancyProp
类型?
对于您的主要问题,在给定对象类型T
和键类型K
情况下查找属性值类型的方法是通过括号语法T[K]
使用查找类型,也就是索引访问类型。 因此,如果您想查找U
类型对象的"obj"
键控属性的"prop"
键控属性的类型,您可以将该类型写为U["obj"]["prop"]
。
请注意,点语法不适用于类型,即使键类型是字符串文字。 如果U.obj.prop
是类型系统中U["obj"]["prop"]
的同义词U.obj.prop
了,但不幸的是,该语法会与 namespaces 发生冲突,因为可能有一个名为U
的命名空间,带有名为obj
子命名空间,具有名为prop
的导出类型,然后U.obj.prop
将引用该类型。
对于您对any
的评论,当Y<T>
的类型参数T
具有泛型约束时,使用X extends Y<any>
并没有错,但它的类型安全性可能比您所能获得的要低一些。 如果类型Y<T>
以协变方式与T
相关,那么您可以使用泛型约束而不是any
。
这意味着,例如, Parent<T extends Obj<any>>
可以替换为Parent<T extends Obj<Prop>>
,而U extends Parent<any>
可以替换为U extends Parent<Obj<Prop>>
.
这些更改为您提供如下代码:
interface Parent<T extends Obj<Prop>> {
obj: T;
}
class Something<U extends Parent<Obj<Prop>>> {
aProp: U['obj']['prop'];
constructor(u: U) {
this.aProp = u.obj.prop;
}
}
我还向Something
添加了一个构造函数,因为应该初始化类属性,并且我想表明当u
是U
时,可以为aProp
分配来自u.obj.pop
的值。
这应该按您的预期工作:
interface PlainObj extends Obj<Prop> { }
interface PlainParent extends Parent<PlainObj> { }
new Something<PlainParent>({ obj: { prop: { a: 1 } } }).aProp.a; // number
interface FancyObj extends Obj<FancyProp> { }
interface FancyParent extends Parent<FancyObj> {
fancy: number;
}
new Something<FancyParent>({ obj: { prop: { a: 1, b: 2 } }, fancy: 3 }).aProp.b; // number
好的,希望有帮助; 祝你好运!
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.