我需要将两个Future [List]合并为一个,我想出了以下解决方案:
def mergeFutureLists[X]( fl1: Future[List[X]], fl2: Future[List[X]] ): Future[List[X]] =
{
val lf = List( fl1, fl2 )
val fll = Future.sequence( lf )
return fll.map{ x => x.flatMap{ el => el } }
}
它做了我想要的,但这是正确的方法吗?
答案 0 :(得分:7)
您可以等待结果,然后将这些结果合并到一个列表中:
def mergeFutureLists[X]( fl1: Future[List[X]], fl2: Future[List[X]] ) = {
for{
f1Res <- fl1
f2Res <- fl2
} yield (f1Res ::: f2Res)
}
答案 1 :(得分:4)
您也可以使用Future.reduce
:
def mergeFutureLists[X]( fl1: Future[List[X]], fl2: Future[List[X]]) = {
Future.reduce(List(fl1, fl2))(_ ++ _)
}
或者,对于任意数量的未来列表:
def mergeFutureLists[X](fl: Future[List[X]]*): Future[List[X]] = {
Future.reduce(fl)(_ ++ _)
}
答案 2 :(得分:1)
我不完全明白你对“正确”的意思,但似乎你正在对未来进行排序。一个更通用的签名:
def mergeFutureLists[X](fl1: Future[List[X]], fl2: Future[List[X]]): Future[List[X]]
可能是:
def mergeFutureLists[X](fl: Future[List[X]]*): Future[List[X]]
您的实施可以用fold
表示为:
def mergeFutureLists[X](fl: Future[List[X]]*): Future[List[X]] =
Future.fold(fl)(List.empty[X])(_ ++ _)
修改强>
与@Kolmar提出的解决方案相比如何?
我们都在++
上下文中使用运算符Future
(列表连接)。实际上@znurgl也在使用伪装的同一个运算符::::
。我们的3个实现的唯一区别是我们如何使用:for-comprehension
,zip
或fold
进入 上下文。
我提出了一个使用fold
(catamorphism)的实现,它可以处理任意数量的参数,以概括您提出的示例。
答案 3 :(得分:1)
仅合并两个List
的最简单方法可能是zip
:
def mergeFutureLists[X](fl1: Future[List[X]],
fl2: Future[List[X]]): Future[List[X]] =
fl1 zip fl2 map Function.tupled(_ ++ _)
答案 4 :(得分:0)
如果两个列表的类型相同,您可以使用Future.collect
:
collect采用一组相同类型的Futures,并生成该类型的一系列值的Future。当所有基础期货已经完成或其中任何一个失败时,这个未来就完成了。返回的序列的顺序对应于传入序列的顺序。
val combinedFuture: Future[Seq[List[X]]] = Future.collect(Seq(fl1, fl1))
然后,您可以在将来返回后将两个列表平面化