Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/347.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
关于';递归地';在java中创建线程-在生成新线程后,是否会对线程进行垃圾收集?_Java_Multithreading - Fatal编程技术网

关于';递归地';在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循环。一切都在后台运行。