gpt4 book ai didi

scala - 如何在 Scala 中清理我死去的 Actor

转载 作者:行者123 更新时间:2023-12-04 20:54:39 24 4
gpt4 key购买 nike

你好
我正在使用 scala(2.8.1) 使用 actor 来实现一个耗时的任务处理程序,但是,在运行我的单元测试时我无法清理它,所以我的单元测试永远挂起。

我如何调用该方法是:

  val configs = new ProjectsConfig("XXXXXXXXXXXXX")
try {
configs.start
configs.init//time consuming stuff
} finally {
configs.destory
configs.stop
}

我打算做的是保持actors的引用并在每个on上调用exit,代码片段是这样的:
  • init,初始化actor并保存每个actor的引用。
  • 销毁,在每个 Actor 上调用退出。
  • 停止,在这个 Actor 上调用退出。

  • 然而,它似乎运行得不好。在这种情况下如何清理所有 Actor ?
    class ProjectsConfig(val url: String) extends Actor {
    private var actors: List[Actor] = List()
    private object Stop

    def init = {
    val caller = this;
    for (projectConfig <- list) {
    val myActor: Actor = actor {
    caller ! projectConfig.instantiate
    }
    actors = actors ::: List(myActor)
    }
    }

    def act() {
    while (true) {
    receive {
    case project: Project =>
    Projects.update(project)
    case Stop => exit()
    }
    }
    }

    def destory {
    for (actor <- actors) {
    try {
    actor ! exit
    } catch {
    case e => System.out.println(e.printStackTrace)
    }
    }
    }

    def stop() {
    this ! Stop
    }

    最佳答案

    1)在你的具体情况下,我会简化

    val myActor: Actor = actor {
    caller ! projectConfig.instantiate
    }

    只是 caller ! projectConfig.instantiate .您已经从 actor 的子系统进行了调用,因此不需要额外的包装。

    除此之外,虽然通常建议从 Actor 的环境中调用 Actor (产生调用), 它根本不是“必须” (如果您直接在非 Actor 环境中调用 Actor ,则不会发生任何邪恶事件)。在您的情况下,包装调用反而会增加问题(样板和不一致)。

    2) actor ! exit中实际发生了什么|是 actor ! Actor.exit ( assuming that you have a wildcard import on Actor )。此代码抛出异常试图评估 Actor.exit ,并且没有任何内容发送给 Actor 。为了阻止 Actor ,您必须调用 exit在它的实例上。它可以通过消息发送来完成,这将调用 protected exit :
    actor{
    loop{
    react{
    case `exit => exit('stop)
    }
    }
    }

    关于scala - 如何在 Scala 中清理我死去的 Actor ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5838960/

    24 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com