Java 等待线程
我有一个包含以下(Java)代码的方法:Java 等待线程,java,multithreading,wait,Java,Multithreading,Wait,我有一个包含以下(Java)代码的方法: doSomeThings()创建一些线程,每个线程只运行有限的时间。问题是我不希望在doSomeThings()启动的所有线程完成之前调用doSomeThings()。(另外,doSomeThings()将调用可能启动新线程的方法等等。在所有这些线程完成之前,我不想执行doSomeOtherThings()) 这是因为doSomeThings()等将myObject设置为null,而doSomeOtherThings()调用myObject.myMeth
doSomeThings()
创建一些线程,每个线程只运行有限的时间。问题是我不希望在doSomeThings()
启动的所有线程完成之前调用doSomeThings()。(另外,doSomeThings()
将调用可能启动新线程的方法等等。在所有这些线程完成之前,我不想执行doSomeOtherThings()
)
这是因为doSomeThings()
等将myObject
设置为null
,而doSomeOtherThings()
调用myObject.myMethod()
,我当时不希望myObject
为null
有没有一些标准的方法来做这种事情(在Java中)?看看Thread.join()
方法
我不清楚您的具体实现,但doSomeThings()似乎应该在返回之前等待子线程
在doSomeThings()方法内部,通过调用Thread.join()方法等待线程
当您创建一个线程并调用该线程的join()方法时,调用线程将等待该线程对象死亡
例如:
// Create an instance of my custom thread class
MyThread myThread = new MyThread();
// Tell the custom thread object to run
myThread.start();
// Wait for the custom thread object to finish
myThread.join();
您可能想看看java.util.concurrent
包。特别是,您可以考虑使用<代码> CurtDutLabCH < /C> >
package de.grimm.game.ui;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class Main {
public static void main(String[] args)
throws Exception {
final ExecutorService executor = Executors.newFixedThreadPool(5);
final CountDownLatch latch = new CountDownLatch(3);
for( int k = 0; k < 3; ++k ) {
executor.submit(new Runnable() {
public void run() {
// ... lengthy computation...
latch.countDown();
}
});
}
latch.await();
// ... reached only after all threads spawned have
// finished and acknowledged so by counting down the
// latch.
System.out.println("Done");
}
}
您可能需要添加异常处理(interruptedexception
)和一些类似的处理。您正在查找的是Executor服务并使用futures:)
看
因此,基本上收集提交给executor服务的所有Runnable的未来。循环所有未来并调用get()方法。当相应的runnable完成时,这些将返回。另一个选项是休眠主线程,并让它经常检查其他线程是否完成。然而,我更喜欢德克和马库斯·亚当斯的答案——为了完整起见,这里就把它抛到这里。另一个有用的、更健壮的、与倒计时闩锁功能类似的功能是。它的工作原理类似于倒计时闩锁,您必须知道使用了多少个参与方(线程),但它允许您在每次创建倒计时闩锁的新实例时重用该屏障
我非常喜欢momania的建议,即使用ExecutorService,收集期货并调用get on所有这些服务,直到它们完成 取决于你在这里到底想做什么。您主要关心的是动态确定从doSomeThings()
中调用的连续方法生成的各种线程,然后能够等到它们完成后再调用dosometherthings()
?或者可以知道编译时生成的线程?在后一种情况下,有很多解决方案,但基本上都涉及从创建线程的任何位置对所有这些线程调用Thread.join()
方法
如果确实是前者,那么最好使用ThreadGroup
及其enumerate()
方法。如果已将新线程正确添加到线程组,则这将为您提供doSomeThings()生成的所有线程的数组。然后,您可以循环遍历返回数组中的所有线程引用,并在调用doSomeOtherThings()
-1调用myThread.run不会启动新线程之前,在主线程上调用join()
。myThread.run()完成时调用myThread.join()只是因为程序顺序,而不是因为任何异步reason@Donal哎呀。谢谢我更新了答案@约翰,对不起,是打字错误。我习惯于从Runnable而不是线程继承。(+1)CountdownLatch
非常方便
package de.grimm.game.ui;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class Main {
public static void main(String[] args)
throws Exception {
final ExecutorService executor = Executors.newFixedThreadPool(5);
final CountDownLatch latch = new CountDownLatch(3);
for( int k = 0; k < 3; ++k ) {
executor.submit(new Runnable() {
public void run() {
// ... lengthy computation...
latch.countDown();
}
});
}
latch.await();
// ... reached only after all threads spawned have
// finished and acknowledged so by counting down the
// latch.
System.out.println("Done");
}
}
boolean done = false;
void functionRunInThreadA() {
synchronized( commonLock ) {
while( !done ) commonLock.wait();
}
// Here it is safe to set the variable to null
}
void functionRunInThreadB() {
// Do something...
synchronized( commonLock ) {
done = true;
commonLock.notifyAll();
}
}