5

我试图让一个演员“去睡觉”,等待另一个演员发出信号。我想做类似的事情:

def act(){
    loop{ //Should I use loop here too??
        if(sleepy){
            react{
                   //SLEEPING
                    case "Wake Up"=> sleepy=false; //just to breack the react
            }
        }else{
            react{
                 //React to other messages
            }
        }
    }
}

现在,当我的演员睡觉时,其他消息会发生什么?他们会被分道扬镳吗?我不想失去他们。什么是解决这个问题的好方法?

4

2 回答 2

6

您可以在反应块中的其他情况下使用保护,反应块中不匹配的消息保存在参与者的消息队列中。请注意,在队列大小过多之前,演员肯定会被“唤醒”。

如果我没记错的话,由于 react 的设计,循环中只能有一个 react 块。

val receiver = new Actor {
  private var sleeping = true

  def act {
    loop {
      react {
        case "Wake Up"       => println("waking up"); sleeping = false
        case x if ! sleeping => println("processing "+x)
      }
    }
  }
}

receiver.start

import Thread.sleep

receiver ! "Message 1"
sleep(2000L)
receiver ! "Message 2"
sleep(2000L)
receiver ! "Wake Up"
sleep(2000L)
receiver ! "Message 3"
sleep(2000L)
receiver ! "Message 4"

唤醒处理 消息 1 处理 消息 2 处理 消息 3 处理 消息 4

于 2010-07-15T15:07:31.560 回答
6

您可以使用与 Don 类似的机制,但可以利用以下andThen提供的功能Actor.Body

def waitForSignal : () => Unit = react { case Signal(_) => }

def processMessages : () => Unit = loop { 
  react {
      case x => //process
  }
}

def act() = waitForSignal andThen processMessages

显式返回类型声明的原因() => Unit是因为react永远不会正常终止(即它返回Nothing)。Nothing位于类型层次结构的底部,是任何其他类型的有效子类型。

我正在利用从 a() => UnitBody包含该andThen方法的类的隐式转换。

于 2010-07-15T19:04:30.263 回答