【问题标题】:RxJava2 idiom for combining two MaybesRxJava2 组合两个 Maybe 的习语
【发布时间】:2018-08-23 15:00:57
【问题描述】:

给定两个 Maybe 值,我如何将它们组合成一个 Maybe

  1. 只要任一源Maybes 调用onSuccess,就调用onSuccess()
  2. 只要两个Maybes调用onComplete()时调用onComplete()

(参见Scala 中的Option.orElse()Vavr。)

例如,假设存在可以满足我要求的 combine() 方法:

combine(Maybe.just(a), Maybe.empty())  ≍ Maybe.just(a)
combine(Maybe.empty(), Maybe.just(b))  ≍ Maybe.just(b)
combine(Maybe.empty(), Maybe.empty())  ≍ Maybe.empty()
combine(Maybe.never(), /*anything*/ )  ≍ /*the thing*/ 
combine(/*anything*/,  Maybe.never())  ≍ /*the thing*/ 

起初我以为 amb() & family 是我要找的东西,但是只要任一源 Maybe 完成,这就会完成,这意味着如果第一个 Maybe 在没有值的情况下完成,你永远不会从第二个Maybe

我现在正在使用

Maybe.mergeArray(m1, m2).firstElement()

这似乎可以满足我的要求,但我不确定它是否正确,也不确定它是否是最干净的方法。 (例如,如果有一些延迟,它会在一个或另一个源调用时立即调用onSuccess(),还是会同时等待onComplete()s?)

这是正确的吗?有没有更惯用的方法?


ETA:我很高兴得到第一个值;我不需要等待两者都完成:

combine(Maybe.just(a), Maybe.just(b))  ≍ Maybe.just(/* a or b, don't care */)

(我可以想象我可能更喜欢其中一种情况,并希望通过参数的顺序来表明这一点,但在这种情况下,我怀疑顺序会比并行更好。)

【问题讨论】:

  • 我相信 zip 函数会在发出结果之前等待来自所有源 observables 的终端事件,如果你想等待所有源的终端事件?
  • @MarkKeen 我不想等待终端事件;如果有价值,我想取先到者。
  • 一个问题是当combine(just(a), never()),第一个代码块中的答案是'never()'。但是在编辑中你说你不等待完成,所以它应该是'just(a)'。您的描述不一致。
  • @DeanXu 说得好。我将编辑该部分。
  • @DavidMoles 你的方法是最好的。唯一的问题是您可以使用merge 而不是mergeArray

标签: java rx-java2 reactivex


【解决方案1】:

有一种稍微不同的方法,可能更接近您的定义。这将使用Observable.switchMapMaybe():

将上游项目映射到MaybeSources 并切换(订阅)到较新的项目,同时处理较旧的项目(并忽略它们的信号),如果可用,则发出当前项目的最新成功值,如果此 Observable 或则立即失败任何活跃的内部MaybeSources 失败。

Observable.just(m1, m2).switchMapMaybe(m -> m).firstElement()

但是使用Maybe.mergeArray(m1, m2).firstElement() 的方法也应该足够了。 firstElement() 操作符发出由 mergeArray() flowable 发出的第一个元素。这个是无序的,因此没有关于完成任何可能的信息。

【讨论】:

  • 我认为mergeArray() 更具可读性,但似乎(在阅读this answer on switchMap() 之后;我认为switchMapXXX 文档需要更多修改)switchMapMaybe() 更准确地捕捉到了意图。
  • 我投了反对票,因为它不满足条件1。例如,当m1 = Maybe.just(1).delay(1, SECONDS)m2 = Maybe.empty<Int>().delay(2, SECONDS) 它会调用onComplete,即使m1 会调用onSuccess
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-07-30
  • 1970-01-01
  • 2018-12-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多