与演员一起处理消息

时间:2013-12-15 15:13:19

标签: scala message akka messages

我有2个演员,演员A向演员B发送消息。演员B然后应处理这些数字并在同一行打印

我的代码:

class ActorB extends Actor{
  def receive = {
     case 0 => println("0")
     case x : Int => println (x)
  }
}

但不会编译

2 个答案:

答案 0 :(得分:2)

你可以这样做:

class ActorB extends Actor with ActorLogging{
  var xs:List[Int] = Nil
  def receive = {
     case x : Int => 
        xs = x :: xs
        if(xs.length==3){
           println(xs.mkString(" ")+" avg: "+xs.sum/3d)
           xs = Nil
        }
  }
}

(我没有测试上面的内容,但它应该给你一个想法)

我认为这可能比使用成为/不成为更容易。您是否有理由想要使用该模式呢?

答案 1 :(得分:1)

你可以这样做(完全未经测试):

class ActorB extends Actor with ActorLogging {

  def receive = {
    case x : Int => context.become(waitingForMore(List(x)))
  }

  def waitingForMore(xs : List[Int]) : Receive = {
    case x : Int if(xs.size == 2) => 
      printResults(x :: xs)
      context.become(receive)

    case x : Int => context.become(waitingForMore(x :: xs))    
  }

  def printResults(xs : List[Int]): Unit = {
    // Do printing here.
  }
}

在这个模型中,您将利用Actors可以改变自己内部行为的事实。您不会显式存储Ints列表,而是将它从函数传递给函数。基本上,演员等待你发送一个Int(receive方法),然后进入一个收集更多结果的状态(waitingForMore方法)。一旦该方法收集得足够多,它就打印结果并返回到receive方法,该方法将重新开始该过程。

编辑根据建议,我只会添加一个小评论,说明为什么我提出这个模型。我觉得你的演员所处的状态更明确地模仿了这个。随着问题的发展和变得越来越复杂,这可能是一个很好的模式。或者它可能没有,因为菲利克斯指出这两种解决方案通过不同的方式得到相同的答案。您应该随意选择您觉得更舒服的解决方案。我表明这一点的目的是为了展示一种更具功能性的替代方法,就是这样。