我想知道JAVA多线程中,如何让一个线程去等待N个线程执行完成后,再执行。

2024-12-22 18:02:51
推荐回答(2个)
回答1:

java.util.concurrent.CountDownLatch 这个类可以实现你所要的功能

例如:CountDownLatch latch = new CountDownLatch(5) //声明计数器为5个
Thread t = new Thread() {
public void run() {
try {
//TODO 你的应用
} catch (Exception e) {
//TODO 异常处理
}
finally {
latch.countDown(); //这句是关键
System.out.println("ok"); //5个线程都跑完后输出
}
}
};
t.start();
然后让以上操作循环五次(就是说同时开5个线程),那么这个"ok"就会在等到这5个线程都ok后才会被输出一次。

回答2:

//1.可用ExecutorService+Future来实现,下面这个限制了最大并发线程数.也可以不限制.
//System.out.println("down");这个位置你可以放那个线程的处理,

//2.用线程锁定也可以.lockunlock lock<线程>unlick

package jp.co.hitachi.jkk.ekarte.hl7.bat;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;

/**
* バッチ自动実行のスレッド
* @author yuangui
* @see Runnable
* @version 0610-00, 2010/8/25
* @since 0610-00
*/
public class CSBatDEMOThread extends Thread {

public static void main(String[] args) {
Thread t = new CSBatDEMOThread();
t.start();
}

/**
* バッチ自动実行
* @return なし
*/
@Override
public void run() {

// CSBProcLock locker = CSBProcLock.createLocker();
ExecutorService es;
try{
// locker.onStart();

//int cpuNums = Runtime.getRuntime().availableProcessors();
//Process 3 threads in the pool
es = Executors.newFixedThreadPool(10);

List> fs = new ArrayList>();

for (int i = 0; i < 100; i++) {
// TODO : logic > Start

TestTask t = new TestTask();
t.setTaskNo(this.toString() + ": " + i);

// TODO : logic End
Future f = es.submit(t);
fs.add(f);
}

for (Future f: fs) {
f.get();
}

//After all submitted tasks are executed,shut down the ExecutorService
if (es.isTerminated()) {
es.shutdown();
}

System.out.println("down");

} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
} finally {
// locker.onEnd();
System.gc();
}
}

}

class TestTask implements Runnable{

String taskNo = "";

@Override
public void run() {
// TODO 自动生成されたメソッド・スタブ

Long wt = Math.round(Math.random() * 1000);
try {

Thread.sleep(wt);
} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}

System.out.println(taskNo + " time:" + wt + "ms");

}

/**
* taskNoを取得します。
* @return taskNo
*/
public String getTaskNo() {
return taskNo;
}

/**
* taskNoを设定します。
* @param taskNo taskNo
*/
public void setTaskNo(String taskNo) {
this.taskNo = taskNo;
}

}