@volatile var breakRequested: Boolean = false
// ...
def futureFunc(): Option[Iterable[String]] = {
val result = hugeList.map { item =>
if(breakRequested) {
// put exit code here
// return None
// throw AnException
// what else?
}
item.toText() // time-expensive function
}
Some(result)
}
Future { futureFunc() }
鉴于有人将breakRequested
标记设置为true
:我如何退出map
?
我尝试了什么:
return None
=>这样的return
转换为scala.runtime.NonLocalReturnControl
:我试图捕捉到这个错误,但它似乎无法捕获(绕过try
/ catch
)。
object Cancelled extends Exception
:我试图抛出这个,但也无法抓住它。
当我通过SBT运行应用程序时,所有异常都显示在命令行中。
如果可能的话,我更喜欢没有try
/ catch
的解决方案。
答案 0 :(得分:1)
对于快速解决方案,您可以将 hugeList 转换为Iterator
,然后使用takeWhile
:
...
val result = hugeList.toIterator
.takeWhile(_ => !breakRequested)
.map { item =>
item.text
}
...
修改强>
Scala的Future
没有取消,但是twitter Future已经取消了。要取消此使用方法raise
。
您也可以编写自己的map
,例如:
@annotation.tailrec def map[T,R](
src: List[T],
cancel: => Boolean,
dsc: List[R] = List.empty[R])(f: T => R):List[R] = src match {
case _ if cancel => dsc
case h :: t => map(t, cancel, f(h) :: dsc)(f)
case Nil => dsc
}
Future{map(hugeList, breakRequested)(_.text)}
如果您不需要结果,则可以创建另一个未来,这将在breakRequested
更改后完成。并使用方法Future.firstCompletedOf
。