【问题标题】:Scala Futures: How to guarantee a non-null result?Scala Futures:如何保证非空结果?
【发布时间】:2023-12-15 06:00:02
【问题描述】:

假设我有一个返回CompleteableFuture[Data]的方法:

def doIt(): CompleteableFuture[Data] = { ... }

而且,doIt() 可以返回 null 的可能性非零。我们如何在不阻塞调用线程的情况下调用doIt() 直到结果不是null? Scala中的方法是什么?

我目前的尝试:

Future {
  var data: Data = null
  blocking {
    while (data == null) { data = doIt().get }
  }
  data
} 

我不想使用blockingget。有什么想法吗?

此外,事后有 map 调用此 Future:

val myFuture = Future {
  var data: Data = null
  blocking {
    while (data == null) { data = doIt().get }
  }
  data
}.map { d => d.someMember } 

d.someMember 将抛出 NullPointerException ,除非我们确保第一个 Future 具有非空结果。

【问题讨论】:

    标签: java scala asynchronous concurrency completable-future


    【解决方案1】:

    使用https://github.com/scala/scala-java8-compat

    import scala.compat.java8.FutureConverters._
    
    def doItNotNull: Future[Data] = 
      doIt.toScala.flatMap {result =>
        if (result == null) doItNotNull // try again
        else Future.successful(result) // wrap in a completed future
      }
    

    【讨论】: