在演员之间切换活动的正确方法是什么。
例如,actorA - 向actorB发送100条消息。 ActorB会将其打印到控制台中。在100条消息之后,actorB将向actorA发送100条消息,而actorA将打印它。每100 msg切换演员行为。
Thansk
答案 0 :(得分:0)
这是我将如何做到的(这是一个非常快速的解决方案,可能不是最优雅的解决方案,欢迎提出改进建议)。主要部分是以下actor,它可以发送或接收消息。它在发送(分别接收)超过Public Class colInfoSet
Inherits CollectionBase
条消息后改变其行为。
numberOfMessages
最初,演员处于一种状态,即它不知道它是发送者还是接收者。在这种情况下,可能会发生两件事:
import akka.actor._
import scala.concurrent.duration._
object SenderReceiver {
case class StartSending(other: ActorRef) // see explanation below
case object TheMessage // dummy placeholder for actual message
case object SendMessage // a reminder for the actor itself to send a message
def props(numberOfMessages: Int): Props = Props(new SenderReceiver(numberOfMessages))
}
class SenderReceiver(numberOfMessages: Int) extends Actor with ActorLogging {
import context._
import SenderReceiver._
// initial receive in order to determine the actor's initial role
def receive = {
case StartSending(other) =>
log.info("I'm sending first, yay!")
sendNext(0, other)
case TheMessage =>
log.info("It seems, I'm receiving messages first.")
become(receiveMessages(1))
}
// receive function for when actor is a receiver of messages
def receiveMessages(messagesReceived: Int) : Receive = {
case TheMessage =>
log.info("Message received")
val messagesReceivedNew = messagesReceived + 1
if (messagesReceivedNew < numberOfMessages - 1)
become(receiveMessages(messagesReceivedNew))
else
sendNext(0, sender)
}
// receive function for when actor is a sender of messages
def sendMessages(messagesSent: Int, other: ActorRef) : Receive = {
case SendMessage =>
other ! TheMessage
log.info("Message sent")
val messagesSentNew = messagesSent + 1
if (messagesSentNew < numberOfMessages - 1)
sendNext(messagesSentNew, other)
else
become(receiveMessages(0))
}
def sendNext(messagesSent: Int, other: ActorRef) {
system.scheduler.scheduleOnce(500 milliseconds, self, SendMessage)
become(sendMessages(messagesSent, other))
}
}
是一个接收者。 become
发件人。一旦演员知道它的角色是什么,它就完全按照它应该做的去做。它发送(或接收)一定数量的消息,然后切换到另一种行为。
为了运行此代码,以下是您可能需要的更多代码段。首先,这里有一个简单的辅助演员设置整个系统并在一段时间后停止它(十秒左右后会变得有点无聊......)
become
而且,为了完整起见,一个简单的object Terminator {
case object StopThem
}
class Terminator extends Actor with ActorLogging {
import Terminator._
import SenderReceiver.StartSending
import context._
val actorA = system.actorOf(SenderReceiver.props(3), "actorA")
val actorB = system.actorOf(SenderReceiver.props(3), "actorB")
actorB ! StartSending(actorA)
system.scheduler.scheduleOnce(10 seconds, self, StopThem)
def receive = {
case StopThem =>
log.info("Stopping actors now")
system.shutdown
}
}
开始一切
App