为 Scala 方法设置超时

Set a timeout for a scala method

我正在尝试为方法设置超时。我在测试中有以下代码。 f的return值是我定义的特殊类型。它 returns Interval(Int, Int)

val f = evalfunc (a, b)

evalfunc 使用外部单纯形求解器。有时它会卡在这里。我想为此设置超时。我在 this 之后尝试了 Future 超时。

def runWithTimeout[T](timeout: Long)(f: => T) : Option[T] = {
 Await.result(Future(f), timeout seconds).asInstanceOf[Option[T]] } 

def runWithTimeout[T](timeout: Long, default: T)(f: => T) : T = { runWithTimeout(timeout)(f).getOrElse(default)}

val f = runWithTimeout(300){evalfunc(a, b)}

但是它说,tools.Interval 不能转换为 scala.Option。如何在此功能中添加计时器?我需要 val f as Interval(Int, Int) 然后我在 f.

上做一些计算

我的问题是我已经尝试使用 link 中给出的解决方案。就我而言,我正在尝试为 returns Interval(Int, Int) 的方法添加超时,它说它需要 scala.Option.

你为什么首先将它投射到 Optiondocumentation for Await.result 表示 result[T] 的 return 类型是 T,而不是 Option[T]

你可以用它做一个 Option[T],但是为此你必须捕获如果 result 方法在指定时间内没有成功抛出的 TimeoutException约束。

也许试试这样的东西:

import scala.concurrent._
import scala.concurrent.duration._

def runWithTimeout[T]
  (timeout: Long)
  (f: => T)
  (implicit ec: ExecutionContext)
: Option[T] = {
  try {
    Some(Await.result(Future(f), timeout.seconds))
  } catch {
    case e: TimeoutException => None
  }
}

注意所有这些超时和等待的东西只影响正在等待的程序部分。它不会以任何方式影响您复杂的数值过程f的执行:一旦启动,它无论如何都会运行,如果它在同一个JVM中运行,则无法停止它,因为JVM是不是操作系统。如果你想能够真正停止f的执行,那么你有两个选择:

  • 使f合作,即偶尔检查结果是否仍然需要,如果超时不再需要结果则停止。
  • 运行 f作为一个单独的进程,在JVM之外,超时后使用操作系统的工具将其杀死。