在Flow中,使用disjoint union类型,我可以使用type refinement根据某个属性选择性地定位联合的子集。
如果我想将所有代码放在一个switch语句中,那就太棒了。但是,如果我想将代码拆分为函数,我不知道如何将类型细化“编码”为类型声明,以便流程“知道”在这些函数中进行了细化。
这是我想要做的一个例子 - 它可以在流动游乐场here上找到。
是否有(非手动,非冗余)方式来声明Thing
或其他语法的子类型,以对类型细化进行编码,以便我可以将其“传递”到{{ 1}}功能?
printThingOfTypeA
答案 0 :(得分:0)
您是否考虑将Thing
的类型拆分为三个定义?
(Try)
type ThingA =
| { type: 'a', a: 1 }
| { type: 'a', a: 2 }
type ThingB =
| { type: 'b', b: 3 }
| { type: 'b', b: 4 }
type ThingC =
| { type: 'c', c: 5 }
| { type: 'c', c: 6 }
type Thing =
| ThingA
| ThingB
| ThingC
printThing({ type: 'a', a: 1 })
// what type do I give thingOfTypeA so that flow refines Thing
// to only the options with type 'a', like in the case 'a': statement?
//
// e.g. Hypothetical syntax: (thingOfTypeA: Thing extends { type: 'a' })
//
function printThingOfTypeA(thingOfTypeA: ThingA) {
// this is fine as all have a type
console.log('type: ' + thingOfTypeA.type)
// how can this 'know' that I've passed a thing of type 'a'
// so that it doesn't fail?
console.log('a: ' + thingOfTypeA.a)
}
这样,您的函数可以接受更具体的ThingA
,而其他代码可以使用更通用的Thing
。
或者,如果你不能将它分开,你可以在函数参数中写一个描述你需要的类型,但是你不能通过任何 {{ 1}}进入它,因为那个东西可能没有必要的属性:
(Try)
Thing