【问题标题】:Composing actors作曲演员
【发布时间】:2011-01-25 14:54:05
【问题描述】:

我已经实现了可以添加到 Actors 的 Listenable/Listener trait。我想知道是否可以将这种风格的特征附加到演员而不必显式调用 listenerHandler 方法?

我也期待在 Akka 库中找到这个功能。我是否遗漏了某些内容,或者 Akka 是否有某些原因不包含此内容?

trait Listenable { this: Actor =>
    private var listeners: List[Actor] = Nil

    protected def listenerHandler: PartialFunction[Any, Unit] = {
        case AddListener(who) => listeners = who :: listeners
    }

    protected def notifyListeners(event: Any) = {
        listeners.foreach(_.send(event))
    }
}

class SomeActor extends Actor with Listenable
{
    def receive = listenerHandler orElse {
        case Start => notifyListeners(Started())
        case Stop => notifyListeners(Stopped())
    }
}

【问题讨论】:

    标签: scala actor akka


    【解决方案1】:

    为什么不直接扩展Actor,或者如果你希望非Actor也可以监听,创建一个ListenableActor来扩展Actor with Listenable?

    然后您将在 Actor 中覆盖receive,就像您在上面所做的那样(除了您还想调用super.receive,不是吗?--您只想修改传入的函数)。

    【讨论】:

    • 这就是问题所在,在这两种情况下,我都必须记住调用 super.receive 或 listenerHanlder。我想知道 Scala 中是否有一种机制或任何 Actor 库允许实现 Listenable 的演员不必做任何事情,除了说:with Listenable
    • 但是你只需要说extends ListenableActor而不是extends Actor;在ListenableActor 中,您已经覆盖了receive(并且可能是receiveWithin)。另见丹尼尔的回答。
    【解决方案2】:

    我建议你扩展 Actor 并使用 abstract override

    【讨论】:

      【解决方案3】:

      这是一个解决方案(来自Beginning Scala的示例的修改版本):

      import se.scalablesolutions.akka.actor.Actor
      
      case class AddListener(who: Actor)
      case class RemoveListener(who: Actor)
      
      class ListenableActor extends Actor {
          private var listeners: List[Actor] = Nil
      
          def receive = {
              case AddListener(who) => listeners ::= who
              case RemoveListener(who) => listeners.filter(_ ne who)
          }
      
          protected def notifyListeners(event: Any) = {
              listeners.foreach(_.send(event))
          }
      }
      
      class ImplementingActor extends ListenableActor {
          override def receive = {
              super.receive orElse {
                  case Message(content) => println(content)
              }
          }
      }
      

      【讨论】:

        【解决方案4】:

        为什么我以前没有见过这个问题,呃,好吧,迟到总比没有好:

        http://doc.akka.io/docs/akka/snapshot/scala/routing.html

        【讨论】:

          【解决方案5】:
          猜你喜欢
          • 2017-12-22
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-02-11
          • 1970-01-01
          相关资源
          最近更新 更多