关于';递归地';在java中创建线程-在生成新线程后,是否会对线程进行垃圾收集?
这是一种可以接受的方法来生产大量的串联螺纹吗关于';递归地';在java中创建线程-在生成新线程后,是否会对线程进行垃圾收集?,java,multithreading,Java,Multithreading,这是一种可以接受的方法来生产大量的串联螺纹吗 public class SomeClass { public static void execute(Job job) { Thread t1 = new Thread(new Runnable()) { public void run() { try { SomeOtherClass.method(job)
public class SomeClass {
public static void execute(Job job) {
Thread t1 = new Thread(new Runnable()) {
public void run() {
try {
SomeOtherClass.method(job)
} finally {
boolean moreToDo = Database.check();
if (moreToDo) {
Job nextJob = Database.fetchNextJob();
SomeClass.execute(nextJob);
}
}
}
}
t1.start();
}
}
我正在尝试运行一系列与应用程序主线程分离的作业。我希望这些作业以串联方式(一个接一个)运行,而不是并行运行,因为我无法控制这些约束。我应该明确指出,这些作业是跨多个实例和会话由用户生成的,作业的信息存储在数据库中
据我所知,这将产生如下线程:
M
|
|
|___1
| |
| |
| |
| |___2
| | |
| X |
| |
| |
| |
| X
|
|
V
M
(main
Thread)将生成线程1
(thread1
),而thread1
将从main
分离,失去所有关联李>
thread1
随后将执行其代码(SomeOtherClass.method(job)
)。它最终将调用其finally
,并检查数据库中的moreToDo
李>
SomeClass.execute()
(由于所有内容都是公共的,所以它可以访问这些内容)李>
thread2
(2
)thread2
随后将执行其代码,SomeOtherClass.method(作业)
李>
thread2
并从thread1
分离后,thread1
将完成执行,并将被排除在垃圾收集之外thread2
将调用finally
语句中的代码。如果它发现moreToDo==false
它的执行将完成,并将被留下进行垃圾收集run()
方法时,它终止并被GC处理,即使它产生了另一个线程
但是你的工人任务不应该既做工作又检查要做的工作。相反,使用生产者/消费者模式,其概念是:
- 创建一个大小受限的
BlockingQueue
- 使用
循环将工作项放入队列while(Database.check())
- 使用size limited
从队列中提取项目并进行处理ExecutorService
- 使用大小限制和阻塞呼叫会对生产者造成反向压力,并限制消费者使用的资源
ExecutorService
并向其提交任务?这似乎让事情变得过于复杂。我想将所有作业的管理完全转移到一个非主线程中。ExecutorService
实现看起来需要由主线程(或专用于它的线程,甚至更复杂)管理,不是吗?这是什么意思,“由主线程管理?”如果您的程序有一个ExecutorService
,则生成任务的任何线程都可以提交任务,ExecutorService最终会执行它。如果你想“串联运行它们”,那么为什么你需要多个线程?@user1676075你是对的,我在写问题时意识到了一个更好的实现。我仍然很好奇,出于学术上的原因,决定发表更多的文章。仅仅因为线程终止,这并不一定意味着控制它的线程
实例有资格进行垃圾收集,或者为其调用堆栈分配的空间将被回收。OP要求证明这些东西都会被回收。我的猜测是,可能是的,但如果不做一些研究,我不能肯定。但是,我从来没有任何理由去做那项研究,因为我会使用一个ExecutorService
。答案很好,但我认为它没有区分线程和线程。GC只回收线程(java.lang.Thread类的实例),而不回收线程,这是操作系统已知的事情,操作系统会清除它使用的资源。@DodgyCodeException在这个问题的上下文中,我们只讨论java线程。感谢您对设计模式的建议。我想我希望将排队的作业保留在数据库中,因为它可以在任何给定作业的执行过程中增长。我所知道的唯一一次检查队列以了解更多信息是在线程完成时。我相信这会使该模式失效,否?@jsarbour否,因为您在自己的线程中运行while循环。一切都在后台运行。