[英]JS Flow: Is inheritance in Flow broken?
考慮一種情況,你有一個B類從A類擴展。你創建一個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。
如果你輸入fooA
方法作為返回this
,那么Flow理解擴展A
類的任何類也將從方法返回自己的實例:
( 試試 )
class A {
fooA (): this {
console.log('fooA called')
return this
}
}
class B extends A {
fooB () {
console.log('fooB called')
return this
}
}
new B().fooA().fooB() // No error
因為您不想更改A
類:另一種簡單的方法是鍵入B
類的fooA
函數以返回B
的實例:
( 試試 )
class A {
fooA () {
console.log('fooA called')
return this
}
}
class B extends A {
fooB () {
console.log('fooB called')
return this
}
fooA: () => B; // Hey Flow, this actually returns a B
}
new B().fooA().fooB() // No error!
函數fooA()返回“this”,它是“A”的一個實例。 如您所知,A類不知道方法fooB存在。 因此,Flow(正確地)指出A中缺少屬性fooB。
您知道事實上,A的這個特定實例也是B的實例,但Flow無法推斷出這一點。 你必須告訴它fooA()返回的A是使用強制轉換的特定場景中的B實例。
將您的調用更改為(new B().fooA(): B).fooB()
應解決Flow錯誤。
Javascript(sans Flow)並不關心這種語義。 當你在fooA()返回的對象上調用“fooB”時,它只是在對象中尋找一個名為“fooB”的方法,它恰好存在,所以它有效,盡管它更容易破壞重構。 流是有用的,因為它會強制您了解被拋出的類型,並在將來為這些問題提供編譯時檢查。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.