according to Java Doc:
CountDownLatch:A synchronization aid that allows one or more threads to wait until a set of operations being performed in other threads completes.
A CountDownLatch is a versatile synchronization tool and can be used for a number of purposes. A code CountDownLatch initialized with a count of one serves as a
simple on/off latch, or gate: all threads invoking await wait at the gate until it is opened by a thread invoking countDown . A CountDownLatch initialized to N can be used to make one thread wait until N threads have completed some action, or some action
has been completed N times.
Another typical usage would be to divide a problem into N parts, describe each part with a Runnable that executes that portion and counts down on the latch, and queue all the Runnables to an Executor. When all sub-parts are complete, the coordinating
thread will be able to pass through await.
sample usage:
package com.test.concurrent;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
public class CountDownLatchTest {
private static final int VISITOR_NUM = 5;
public static void main(String[] args) {
/*
* all visitor end visiting, visiting end
*/
CountDownLatch end = new CountDownLatch(VISITOR_NUM);
Visitor[] plays = new Visitor[VISITOR_NUM];
for (int i = 0; i < VISITOR_NUM; i++) {
plays[i] = new Visitor(i + 1, end);
}
System.out.println("begin....");
ExecutorService exe = Executors.newFixedThreadPool(VISITOR_NUM);
for (Visitor p : plays) {
exe.execute(p);
}
try {
long startTime = System.currentTimeMillis();
System.out.println(Thread.currentThread() + "*****"+startTime+" waiting for visiting end....");
// end.await();// wait till count ==0
end.await(1,TimeUnit.SECONDS);// waiting 1 second, end wait, go on
System.out.println(Thread.currentThread() +"*****"+(System.currentTimeMillis() - startTime)+" end waiting....");
long count = end.getCount();
if(count > 0){
System.out.println(Thread.currentThread() + "*****" + "still " + count + " visitor(s) not end visiting!!");
} else {
System.out.println(Thread.currentThread() + "*****" + "all visitors are end now");
}
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
System.out.println("結束");
}
System.out.println("next batch can start");
exe.shutdown();
}
}
class Visitor implements Runnable {
private int id;
private CountDownLatch end;
public Visitor(int id, CountDownLatch end) {
super();
this.id = id;
this.end = end;
}
public void run() {
try {
System.out.println(Thread.currentThread() + "===" + System.nanoTime()+" visitor " + id +" begin visiting..");
Thread.sleep((long) (Math.random() * 2000));//visiting time
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
System.out.println("visitor " + id + " has finished visiting. ");
end.countDown();// visiting done
}
}
}