1

インスタンスを保持するために var を使用せずに、自己キャンセル ポーラーを安全に実装できるかどうか興味があります。akka.actor.Cancellable

これまでのところ、以下の例に示すようなものを思いつきました。ただし、ホットスワップが発生する前、つまりポーラーをスケジュールする行の前に「ティック」メッセージがディスパッチされることはないと想定しても安全かどうか、興味があります。

tick(1, 5, context.system.scheduler.schedule(Duration.Zero, 3 seconds, self, "tick"))

基本的には次と同じです:

val poll = context.system.scheduler.schedule(Duration.Zero, 3 seconds, self, "tick")
tick(1, 5, poll)

したがって、場合によっては、ホットスワップが発生する前に最初のティックが受信されると思います...

import akka.actor.{Cancellable, ActorSystem}
import akka.actor.ActorDSL._
import concurrent.duration._

object PollerDemo {
  def run() {
    implicit val system = ActorSystem("DemoPoller")
    import system.dispatcher

    actor(new Act{
      become {
        case "tick" => println("UH-OH!")
        case "start" =>
          become {
            tick(1, 5, context.system.scheduler.schedule(Duration.Zero, 3 seconds, self, "tick"))
          }
      }
      def tick(curr:Long, max:Long, poll:Cancellable):Receive = {
        case "tick" => {
          println(s"poll $curr/$max")
          if(curr > max)
            cancel(poll)
          else
            become{ tick(curr + 1, max, poll) }
        }
      }
      def cancel(poll:Cancellable) {
        println("cancelling")
        poll.cancel()
        println(s"cancelled successfully? ${poll.isCancelled}")
        println("shutting down")
        context.system.shutdown()
      }
    }) ! "start"

    system.awaitTermination(1 minute)
  }
}
4

2 に答える 2

3

私の推測では、あなたのコードは問題ないと思います。アクターは一度に 1 つのメールボックスのみを処理することに注意してください。メッセージを受信したら、start別のメッセージをメールボックスに配信するタイマーを設定してから、受信の実装を交換します。メッセージの処理中に受信スワップを行うためstart、アクターがメールボックス内の次のメッセージを処理する前に、アクターの受信動作が既に変更されています。したがって、メッセージの処理に移るとtick、新しい受信動作が使用されることを確認できます。

次のようtickに、最初の内部に追加のメッセージを送信することで、これを確認できます。become

become {
  self ! "tick"
  tick(1, 5, context.system.scheduler.schedule(Duration.Zero, 3 seconds, self, "tick"))
}

ここでは、become ブロック中に送信されたメッセージが古い受信または新しい受信によって処理されるかどうかを尋ねるときに、式からタイマーを実際に削除しています。私はこれを実行しませんでしたが、私の理解または akka から、これらのティックは両方とも新しい受信によって処理される必要があります。

于 2013-06-16T10:59:53.350 に答える