在我的项目中,我使用映射类型(以 string
作为键):
export type ConfigurableFieldsType<T extends string[]> = {
[field in keyof T]: string
}
在以下方法中,我使用类型(this.configurableFields
是一个 ConfigurableFieldsType
对象):
private getConfigurableAttribute(attribute: C[number]): string {
return this.configurableFields[attribute]
}
但是,我收到错误:
Type 'C[number]' cannot be used to index type 'ConfigurableFieldsType<C>'.
您可以在 TS Playground 中找到完整的示例(带有可重现的错误)或以下内容:
export type ProductType<T extends string[]> = {
// more variables
configurableFields: ConfigurableFieldsType<T>
}
export type ConfigurableFieldsType<T extends string[]> = {
[field in keyof T]: string
}
export class Product<C extends string[]> implements ProductType<C> {
constructor(
// more public parameters
public configurableFields: ConfigurableFieldsType<C>,
) {}
private getConfigurableAttribute(attribute: C[number]): string {
return this.configurableFields[attribute]
}
}
最佳答案
您打算ConfigurableFieldsType<["a", "b", c"]>
评估类似 {a: string, b: string, c: string}
,但您当前的定义将导致 [string, string, string]
。那是因为{[K in keyof T]: string}
结果是 mapped array type ; T
是一个类似数组的类型,并且 keyof T
因此是数组键,例如 "push"
或"length"
.
相反,您希望类型的键是 T
的元素 。也就是说,当你 index into 时你得到的类型T
带有数字索引...所以而不是 keyof T
,你想要T[number]
:
export type ConfigurableFieldsType<T extends string[]> = {
[K in T[number]]: string
}
type Example = ConfigurableFieldsType<["a", "b", "c"]>
/* type Example = {
a: string;
b: string;
c: string;
} */
现在一切都按照您的预期进行了:
private getConfigurableAttribute(attribute: C[number]): string {
return this.configurableFields[attribute] // okay
}
关于javascript - T 将 String 扩展为映射类型的索引,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73042334/