- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我正在开发一个可以同时打开多个模型的扩展。模型可以动态打开和关闭。模型作为 LiteWorkspace
打开,以便显示小部件等。每当您创建新的 LiteWorkspace
时,它都会启动 JobThread
和 Lifeguard
。问题在于关闭 GUIWorkspace(LiteWorkspace 的父类)并不会终止其 Lifeguard 或 JobThread。
可能的解决方案:
理想的解决方案是让所有模型共享一个 JobThread
,因为这将消除线程数量作为一个可以运行的模型数量的上限。这样做也会带来一定的性能优势。这有可能吗?此解决方案仍然需要能够杀死Lifeguard
。
接下来当然是能够杀死线程。
作为最后的手段,我们可以保留一个 GUIWorkspace
池。当用户关闭模型时,它会被扔回池中。然后,当用户加载新模型并且池中有东西时,我们只需重用其中一个 GUIWorkspace。这将允许我们打开与 2 相同数量的模型。唯一的缺点是打开一个新模型(例如从文件菜单或其他什么方式打开一个新模型)仍然不会杀死线程,因此存在永久资源包袱。实际上,出于性能原因,我们可能必须建立一个池,但如果能够在某个时候真正释放资源,那就太好了。
最佳答案
解决方案 1 不可行;每个工作区一个 JobThread 的假设深深嵌入到代码中。
要让 JobThread 终止,这应该足够了:
workspace.jobManager.haltPrimary()
workspace.jobManager.die()
要让 GUIWorkspace.Lifeguard 线程终止,我们只需要对其调用 interrupt()
即可,但即使只是获取对它的引用也不是那么容易。这是显示成功尝试的记录:
/Applications/NetLogo 5.0.5 % scala29 -Yrepl-sync -classpath NetLogo.jar
Welcome to Scala version 2.9.3 (Java HotSpot(TM) 64-Bit Server VM, Java 1.7.0_51).
scala> val applet = new org.nlogo.lite.Applet
applet: org.nlogo.lite.Applet = ...
scala> applet.init()
...
scala> val ws = applet.panel.workspace: org.nlogo.window.GUIWorkspace
ws: org.nlogo.window.GUIWorkspace = org.nlogo.lite.LiteWorkspace@69cafecd
scala> import collection.JavaConverters._
import collection.JavaConverters._
scala> Thread.getAllStackTraces().keySet.asScala.foreach(println)
Thread[JobThread,4,main]
Thread[Lifeguard,6,main]
...
scala> ws.jobManager.haltPrimary()
scala> ws.jobManager.die()
scala> import util.Try
import util.Try
scala> for {
thread <- Thread.getAllStackTraces().keySet.asScala
if thread.getName == "Lifeguard"
outer = Try{ val field = thread.getClass.getDeclaredField("this$0")
field.setAccessible(true)
field.get(thread) }
if outer.toOption == Some(ws)
} {
thread.interrupt()
thread.join()
}
Success(org.nlogo.lite.LiteWorkspace@69cafecd)
scala> Thread.getAllStackTraces().keySet.asScala.foreach(println)
...
(请注意,我已经在 Scala 中回答了;转换为 Java 留给了读者。用于访问内部类的外部实例的反射内容来自 https://stackoverflow.com/a/763617/86485 。)
欢迎以更简洁的方式添加实现 GUIWorkspace.dispose()
的代码的拉取请求。
关于java - 在 NetLogo 扩展中兼顾 JobThreads 和 GUIWorkspaces,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21815690/
我正在开发一个可以同时打开多个模型的扩展。模型可以动态打开和关闭。模型作为 LiteWorkspace 打开,以便显示小部件等。每当您创建新的 LiteWorkspace 时,它都会启动 JobThr
我是一名优秀的程序员,十分优秀!