【发布时间】:2018-05-10 00:20:16
【问题描述】:
假设您有一个从类 A 扩展而来的类 B。您创建 B 类型的对象并调用 A 中定义的方法 fooA,然后调用 B 中定义的方法 fooB。
class A {
fooA () {
console.log('fooA called')
return this
}
}
class B extends A {
fooB () {
console.log('fooB called')
return this
}
}
new B().fooA().fooB()
运行时,代码按预期记录以下内容
fooA called
fooB called
所以 Javascript 理解 new B().fooA() 是 B 类的对象。但是 Flow 给了我以下错误消息:
Cannot call new B().fooA().fooB because property fooB is missing in A
怎么办?我对不需要更改父类 A 的解决方案感兴趣,因为它是在 npm 包中定义的。不过我可以换B。
【问题讨论】:
-
我不使用 flow,但我倾向于认为它的行为正确。考虑到
A是超类型,它不知道B;它只知道this是A,并且可以是任何类型的子类型。所以从静态类型安全的角度来看,此时的类型系统无法知道fooA的结果也是B实例。 -
我不会说 JavaScript“理解”任何关于类型的东西。除了运行时存在的类型安全之外,它没有内置的类型安全性。在编译时,它只是让你为所欲为。
-
FWIW,将
fooA注释为fooA (): this解决了这个问题。 -
作为一种解决方法,您可以将成员
fooA: () => B;添加到B类。更好的解决方案是为此 npm 包提供类型
标签: javascript inheritance flowtype