2

Scalaでは、リモートアクターに接続するのは非常に簡単ですが、ドキュメントには切断について何も書かれていません。リモートアクターはアクターであるため、参照を破棄するだけでは機能しません。したがって、これらは停止されるまで収集されません。では、どうすれば切断できますか?

これは終了後に終了しません:

import actors.{DaemonActor,remote}
import remote.{RemoteActor,Node}

object SimpleClient{
    val messageHandler = new DaemonActor{
        def act{
            loop{
                react{
                    case message:String =>
                        println("got message: " + message)
                    case _ =>
                }
            }
        }
        start
    }

    def main(args:Array[String]){
        val server = RemoteActor.select(Node("localhost",9999),'server)
        server.send('Connect,messageHandler)

        var exit = false
        while(!exit){
            val message = Console.readLine
            if(message == "exit" || message == "quit") {
                exit = true
                server ! 'Disconnect
            }
            else
                server ! message
        }
    }
}

これはサーバーです:

import actors.{Actor,OutputChannel}
import actors.remote.RemoteActor

object Server extends Actor{
    val clients = new collection.mutable.HashSet[OutputChannel[Any]]
    def act{
        loop{
            react{
                case 'Connect =>
                    clients += sender
                case 'Disconnect =>
                    clients -= sender
                case message:String =>
                    for(client <- clients)
                        client ! message
            }
        }
    }

    def main(args:Array[String]){
        start
        RemoteActor.alive(9999)
        RemoteActor.register('server,this)
    }
}
4

4 に答える 4

3

[免責事項:私はAkkaのPOです]

初日からリモートアクターを念頭に置いて構築されたAkkaを見てみることをお勧めしますか?www.akka.io

于 2010-12-03T13:13:44.577 に答える
2

あなたの質問は、あなたが経験していると思う問題について十分に明確ではありません。アクターは(ソケットのように)互いに「接続」しません。アクターへの参照(またはリモートアクターの場合はプロキシ)があるため、アクターにメッセージを送信します。

このような参照があるからといって、アクター(いずれかのアクター)がシャットダウンするのを防ぐことはできません。アクターへの参照がなくなり、実行されていない場合、ガベージコレクションを停止することはできません。

于 2010-12-02T22:40:46.160 に答える
2

Reactorトレイトはprotected[actors] def exit(): Nothing、アクターがそうするように指示するメッセージを受信したときに、どのアクターが自分自身を呼び出すことができるかを定義します。

sealed trait Msg
case object Apoptosis extends Msg
// ... more messages


class RRActor extends Reactor[Msg] {
  def act =  loop {
    react {
      // ... Whatever messages the actor handles
      case Apoptosis => this.exit
    }
  }
}

編集:私はこれまでリモートアクターでこれをテストしていません。

于 2010-12-03T03:38:04.380 に答える
1

これがソースの作業バージョンであり、関連する変更がインラインでコメントされています。

import actors.{DaemonActor,remote}
import remote.{RemoteActor,Node}

case class Send(message: String)
case object Disconnect

object SimpleClient{
    val messageHandler = new DaemonActor{

       def act{
          // keep the reference to the proxy inside the client-side actor
          val server = RemoteActor.select(Node("localhost",9999),'server)
          server ! 'Connect
          loop{
             react{
                case message:String =>
                   println("got message: " + message)
                case Send(message) => server ! message
                case Disconnect => { 
                   // disconnect and exit the client-side actor
                   server ! 'Disconnect //'
                   exit
                }
                case _ =>
              }
          }
      }
      start
   }

   def main(args:Array[String]){
      var exit = false
      while(!exit){
         val message = Console.readLine
         if(message == "exit" || message == "quit") {
            exit = true
            // tell the client-side actor to exit
            messageHandler ! Disconnect
         } else {
            messageHandler ! Send(message)
         }
      }
   }
}
于 2010-12-05T03:58:54.150 に答える