从您提供的代码示例中,我不能 100% 确定您要完成什么。您似乎正在尝试为Actor
提供的范围内的每个值设置一个值,并通过打印出提供的值来对消息做出反应。
鉴于此,您的代码存在一些问题。主要问题是缺少loop{}
闭包,它确保Actor
在处理完一条消息后等待下一条传入消息。
其次,调用stop()
也无济于事。它只是阻止Actor
接收附加消息。它不会对您造成任何伤害,因为您会立即调用 join,但这会增加混乱。
为了使它工作,这里是您的代码简化为一个工作示例:
import groovyx.gpars.actor.Actors
def a = 1
def b = 100000
def actor = Actors.actor {
loop {
react {
println it
}
}
}
(a..b).each {
actor << it
}
actor.join()
在此示例中,对于范围内的每个值,都会向参与者添加一条消息,该参与者通过打印值来响应消息,然后由于“循环”闭包而等待下一个传入消息。
所以这个例子应该完成你想要的。但是,为了更清楚地了解您的代码中发生了什么,这里有一个解释。
当您Actor
对消息做出“反应”时,您正在向Reactor
. 即使您没有显式返回值,在 Groovy 中,闭包中的最后一行是 return 语句。结果,由于您在 Closure 中的最后一行是 a println
,因此返回的是 null。因此,您Reactor
返回 null,它被视为发送给 theActor
并再次处理的消息。
为避免这种情况,您需要评估返回消息并仅委托消息/或在尚未处理时打印它。我已经更新了您的代码,为了清楚起见,故意返回“完成”作为返回消息。null
您可以更改代码以在处理消息之前仅检查消息:
导入 groovyx.gpars.actor.Actors
def a = 1
def b = 100000
def reactor2 = Actors.reactor { message ->
if(!message.equals("done")) {
println "\t\tReact Again: $message"
}
return "done"
}
def reactor = Actors.reactor { message ->
if(!message.equals("done")) {
println "\tReact: $message"
reactor2 << message
}
return "done"
}
def actor = Actors.actor {
loop {
react {
if(!it.equals("done")) {
println it
reactor << it
}
}
}
}
(a..b).each {
actor << it
// actor.oi
}
actor.join()