1

我想向演员发送消息列表,在未来立即收到回复,然后等待所有未来完成,然后再返回调用方法。通过阅读 akka 文档,我相信 Future.sequence 是要走的路,但我无法让以下代码正常工作。我从编译器得到这个错误:

  found   : akka.dispatch.ActorCompletableFuture
  required: akka.dispatch.Future[Integer]
Error occurred in an application involving default arguments.
            futures += secondary ? GetRandom
                                 ^

我确定我遗漏了一些明显的东西,但是根据示例和 API 文档,下面的代码似乎是“正确的”。

import java.util.Random
import akka.dispatch.Future
import akka.actor._
import Commands._
import collection.mutable.ListBuffer

object Commands {
    trait Command

    case class GetRandom() extends Command
    case class GenRandomList() extends Command  
}

class Secondary() extends Actor {
    val randomGenerator = new Random()

    override def receive = {
        case GetRandom() =>
            self reply randomGenerator.nextInt(100)
    }
}

class Primary() extends Actor {
    private val secondary = Actor.actorOf[Secondary]

    override def receive = {

        case GenRandomList() =>

            val futures = new ListBuffer[Future[Integer]]

            for (i <- 0 until 10) {
                futures += secondary ? GetRandom
            }

            val futureWithList = Future.sequence(futures)

            futureWithList.map { foo =>
                println("Shouldn't foo be an integer now? " + foo)
            }.get
    }

    override def preStart() = {
        secondary.start()
    }
}

class Starter extends App {
    println("Starting")
    var master = Actor.actorOf(new Primary()).start()
    master ! GenRandomList()
}

向演员发送一系列消息,接收未来并在所有未来完成后返回的正确方法是什么(可选地将每个未来的结果存储在列表中并返回它)。

4

2 回答 2

3

Akka?返回 aFuture[Any]但你需要一个Future[Int].

因此,您可以定义一个接受各种期货的列表:

val futures = new ListBuffer[Future[Any]]

Int尽快将结果转换为:

for (i <- 0 until 10) {
  futures += (secondary ? GetRandom) map {
    _.asInstanceOf[Int]
  }
}

顺便说一句,要使其工作,您需要更改GetRandom定义:

case object GetRandom extends Command

并将其与:

case GetRandom =>
于 2011-10-12T07:48:57.857 回答
3
(secondary ? GetRandom).mapTo[Int]
于 2011-10-12T08:39:32.153 回答