【发布时间】:2018-02-07 12:57:35
【问题描述】:
为什么构造函数签名与以下摘录中的接口声明不匹配,我应该如何重新表达它?报错是
'Class 'Item' 错误地实现了接口 'ItemClass'。 类型“项目”不匹配签名“新(范围?:范围 | 未定义):项目”。
这段代码的重点是工厂支持在运行时由来自类序列化的字符串名称标识的子类。抽象的 AsyncCtor 定义并初始化了一个 Ready 属性。我可以直接在
export interface ItemClass {
Ready: Promise<any>;
new(Scope?: Scope): Item;
}
export abstract class AsyncCtor {
public Ready: Promise<any> = new Promise((resolve, reject) => resolve(undefined));
}
export abstract class Item extends AsyncCtor implements ItemClass {
static Type: Map<string, ItemClass> = new Map<string, ItemClass>();
static register(typeName: string, typeClass: ItemClass): void {
this.Type.set(typeName, typeClass);
}
public static new(raw: any): Item {
let graph = typeof raw === "string" ? JSON.parse(raw) : raw;
let typeClass = Item.Type.get(graph.Type) as ItemClass;
let item = new typeClass();
...
return item;
}
constructor(public Scope?: Scope) {
super();
}
}
如果我停止声明 Item 实现 ItemClass 的事实,一切都会编译并且 Item.new(raw) 方法工作正常,所以显然它确实实现了 ItemClass。
在有人建议之前,我已经尝试过了
constructor(public Scope?: Scope | undefined) {
【问题讨论】:
-
谢谢。在我看来,我的问题几乎是重复的,其主要优点是它将帮助来自这个方向的人们找到理解。如果您愿意重申您的评论作为答案,我愿意接受。
-
Nitzan 的答案是正确的,当您在
Item中有正确的constructor和正确的静态方法时,Item的静态部分符合ItemClass,您可以使用任何Item的非抽象后代作为register的第二个参数,没有明确声明它实现了ItemClass(打字稿中的兼容性始终是结构性的)。另见stackoverflow.com/questions/39362690/…
标签: typescript constructor interface