CountDownLatch類是一種靈活的閉鎖實現,它可以使一個或多個線程等待一組事件發生。閉鎖狀態包括一個計數器,該計數器被它的唯一的構造方法CountDownLatch(int count)初始化爲一個正數,表示需要等待的事件數量。當在閉鎖上調用await()方法時掛起線程,直到等待閉鎖計數器爲0才接着執行。當在閉鎖上調用countDown()方法時,閉鎖的計數器將減1,當閉鎖計數器爲0時,閉鎖將打開,所有線程將通過閉鎖開始執行。
public class PerformanceTestTool {
public long timecost(final int times, final Runnable task) throws InterruptedException {
if (times <= 0) throw new IllegalArgumentException();
final CountDownLatch startLatch = new CountDownLatch(1);
final CountDownLatch overLatch = new CountDownLatch(times);
for (int i = 0; i < times; i++) {
new Thread(new Runnable() {
public void run() {
try {
startLatch.await();
//
task.run();
} catch (InterruptedException ex) {
Thread.currentThread().interrupt();
} finally {
overLatch.countDown();
}
}
}).start();
}
//
long start = System.nanoTime();
startLatch.countDown();
overLatch.await();
return System.nanoTime() - start;
}
}
在上面的例子中使用了兩個閉鎖,第一個閉鎖確保在所有線程開始執行任務前,所有準備工作都已經完成,一旦準備工作完成了就調用startLatch.countDown()打開閉鎖,所有線程開始執行。第二個閉鎖在於確保所有任務執行完成後主線程才能繼續進行,這樣保證了主線程等待所有任務線程執行完成後才能得到需要的結果。在第二個閉鎖當中,初始化了一個N次的計數器,每個任務執行完成後都會將計數器減一,所有任務完成後計數器就變爲了0,這樣主線程閉鎖overLatch拿到此信號後就可以繼續往下執行了。