Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/364.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,我有一组java线程,我想运行几次(每次都使用不同的参数集)。要开始第二次跑步,我要等待第一次跑步结束。这应该在第二次运行之前通过Thread.join()轻松完成,但由于我的线程在无限循环中运行,我必须通过中断来停止它们,这也会中断阻塞连接: 我有一个线程,其run()方法基本上如下所示: try { while(true) { printSomeInfo(); if (...) { Thread.currentThrea

我有一组java线程,我想运行几次(每次都使用不同的参数集)。要开始第二次跑步,我要等待第一次跑步结束。这应该在第二次运行之前通过
Thread.join()
轻松完成,但由于我的线程在无限循环中运行,我必须通过中断来停止它们,这也会中断阻塞连接:

我有一个线程,其
run()
方法基本上如下所示:

try {  
    while(true) {  
        printSomeInfo();
        if (...) {
            Thread.currentThread().getThreadGroup().interrupt();
        }
    } 
} catch (InterruptedException e) {  
    Thread.currentThread().getThreadGroup().interrupt();  
} finally {  
    printStats();
}
New run:
Info 1
Info 1
...
Info 1
New run:
(here comes the stack trace)
Info 2
Info 2
Stats 1    <- this should happen before the second "New run:"
...
Info 2
Stats 2
以及调用线程的run方法的main方法:

System.out.println("New run:");
for (i ...) {    //first run
    myThread[i] = new MyThread(someInfoString1);
    myThread[i].start();
}
try {
    for (i...) {
        myThread[i].join();
    }
} catch (InterruptedException e) {
    e.printStackTrace();
}
System.out.println("New run:");
for (i ...) {    //second run
    myThread[i] = new MyThread(someInfoString2);
    myThread[i].start();
}
try {
    for (i...) {
        myThread[i].join();
    }
} catch (InterruptedException e) {
    e.printStackTrace();
}
我的问题是,第二次运行开始打印信息,而第一次运行没有使用finally块中的printStats()方法完成打印。 因此,输出如下所示:

try {  
    while(true) {  
        printSomeInfo();
        if (...) {
            Thread.currentThread().getThreadGroup().interrupt();
        }
    } 
} catch (InterruptedException e) {  
    Thread.currentThread().getThreadGroup().interrupt();  
} finally {  
    printStats();
}
New run:
Info 1
Info 1
...
Info 1
New run:
(here comes the stack trace)
Info 2
Info 2
Stats 1    <- this should happen before the second "New run:"
...
Info 2
Stats 2
新运行:
信息1
信息1
...
信息1
新运行:
(这里是堆栈跟踪)
信息2
信息2

Stats 1问题在于重复使用
Thread.currentThread().getThreadGroup().interrupt()
,它会中断
ThreadGroup
中的所有线程,包括调用
join
的线程

如果查看循环,您正在捕获
中断异常
,但没有正确恢复。循环包含在
try…catch
块中,因此被异常强制终止。由于要在所有线程上调用
join
,因此必须继续循环,包括已中断的
join
调用:

threads: for (i...) { // loop over all threads
    for(;;) { // recover join on InterruptedException
        try {
            myThread[i].join();
            continue threads; // after successful join
        } catch (InterruptedException e) {} // call join again
    }
}

通常,中断整个
线程组
,或者处理过时的线程组概念,都不是一种正确的软件设计。你应该重写你的软件,只中断插入的线程。或者简单地使用并发框架,特别是
ExecutorService
,它已经提供了提交任务组和取消或等待所有任务的方法。

如果一段代码必须在另一段之后运行,为什么不使用一个线程呢?因为有些部分应该并行完成?OP正在使用一个线程来编排其他线程。