【问题标题】:Scala Listener/ObserverScala 监听器/观察器
【发布时间】:2011-04-14 21:40:18
【问题描述】:

通常,在 Java 中,当我有一个向其他对象提供某种通知的对象时,我将使用侦听器/观察者模式。

有没有更类似于 Scala 的方式来做到这一点?我应该在 Scala 中使用这种模式,还是在我应该利用的语言中加入其他东西?

【问题讨论】:

    标签: scala listener observer-pattern


    【解决方案1】:

    您仍然可以累积回调列表,但您可以让它们成为函数,而不必再想出另一个单一的方法接口。

    例如

    case class MyEvent(...)
    
    object Foo { 
      var listeners: List[MyEvent => ()] = Nil
    
      def listen(listener: MyEvent => ()) {
        listeners ::= listener
      }
    
      def notify(ev: MyEvent) = for (l <- listeners) l(ev) 
    }
    

    如果您想服用红色药丸,也请阅读此this somewhat-related paper。 :)

    【讨论】:

    • 您可以将其很好地提取到 Publisher 特征中。
    【解决方案2】:

    有没有更类似于 Scala 的方式来做到这一点?

    是的。阅读 Ingo Maier、Tiark Rompf 和 Martin Odersky 的论文Deprecating the Observer Pattern

    2015 年 4 月 27 日更新: 还有一个更新的 Deprecating the Observer Pattern with Scala.React 由 Maier 和 Odersky 撰写。

    【讨论】:

    • 您能举个例子吗?
    • @cdmckay scala.swing 标准库中的包就是基于它。查看其示例和教程。
    【解决方案3】:
    trait Observer[S] {
         def receiveUpdate(subject: S);
    }
    
    trait Subject[S] {
         this: S =>
         private var observers: List[Observer[S]] = Nil
         def addObserver(observer: Observer[S]) = observers = observer :: observers
    
         def notifyObservers() = observers.foreach(_.receiveUpdate(this))
    }
    

    这个 sn-p 非常类似于在 Java 中找到的带有一些 Scala 特性的。这是来自 Dean Wampler 的博客 - http://blog.objectmentor.com/articles/2008/08/03/the-seductions-of-scala-part-i

    这使用了一些 Scala 特性,例如用 [S] 表示的泛型,类似于 Java 接口但更强大的特性,:: 将观察者添加到观察者列表中,以及使用 _ 的参数的 foreach对当前观察者求值。

    【讨论】:

      【解决方案4】:

      您可以使用 scala.collection.mutable.Publisher 和 scala.collection.mutable.Subscriber 来创建 pub/sub 实现

      【讨论】:

      • @ziggystar,还有?你的经历是什么?
      • 我想我没有让它工作或者使用起来很烦人。我现在正在使用第三方库或滚动自己的库。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-19
      • 1970-01-01
      • 1970-01-01
      • 2011-04-26
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多