gpt4 book ai didi

scala futures - 如何从两个 future 中获得结果或失败

转载 作者:行者123 更新时间:2023-12-01 07:40:37 25 4
gpt4 key购买 nike

我正在使用 for 并行运行 2 个 future 。我想知道在所有情况下哪些成功了,哪些失败了(所有情况都应该运行直到完成,并显示结果或失败状态)。目前我只能检索到一个组合的成功结果

我从这里得到启发,但这还不够,因为当一个失败时我没有获得成功状态,在两个都失败的情况下我也没有获得两个失败 failure in Scala future's for comprehension

case class TaggedException(context:String, val throwable: Throwable) extends Exception(throwable.getMessage)

val f1 = Future {...}.recoverWith {case e:Throwable => Future.Failed(new TaggedException("first one failed", e))}
val f2 = Future {...}.recoverWith {case e: Throwable => Future.Failed(new TaggedException("second one failed", e))}

val combinedResult = for {
r1 <- f1
r2 <- f2
} yield (r1,r2)

combinedResult.onFailure {
case e : TaggedException => ... // if both fail I only get the first line in the for
// in case where single fails I only know fail status without the success of the second
}

我正在努力避免这种困惑:

var countCompleted = 0 ... or some other atomic way to count 
f1 onComplete {
case Success(value) => {
... countCompleted increment ...
// handle success
if both completed {
// handle returning a status
}
}
case Failure(error) => {
... countCompleted increment ...
// handle failure
if both completed {
// handle returning a status
}
}
}

f2 onComplete {
case Success(value) => {
... countCompleted increment ...
// handle success
if both completed {
// handle returning a status
}
}
case Failure(error) => {
... countCompleted increment ...
// handle failure
if both completed {
// handle returning a status
}
}
}

编辑:另一个版本 - 这是一种有效的方法吗?

def toFutureTry[A](future: Future[A]):Future[Try[A]] = future.map(Success(_)).recover {case t: Throwable => Failure(t)}

val fa: Future[Try[Blah]] = toFutureTry(f1)
val fb: Future[Try[Foo]] = toFutureTry(f2)

val combinedRes = for {
ra <- fa
rb <- fb
} yield (ra,rb)

combinedRes.onComplete {
case Success(successRes: (Try[Blah], Try[Foo])) => // all of these cases are success or fails
case Failure(f: Throwable) => // i think it is unused right?
}

最佳答案

你可以像这样组合transformzip:

val combinedResult: Future[(Try[T], Try[T])] =
f1.transform(Success(_)).zip(f2.transform(Success(_)))

然后你可以这样做:

combinedResult map {
case (Success(v1), Success(v2)) =>
case (Success(v1), Failure(f2)) =>
case (Failure(f1), Success(v2)) =>
case (Failure(f1), Failure(f2)) =>
}

关于scala futures - 如何从两个 future 中获得结果或失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55626630/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com