現在有十個線程各自輸出0-50000中的所有偶數,假設我們試圖使用下面這段代碼計算整個程式的執行時間:
package concurrent;
class LatchDemo implements Runnable {
@Override
public void run() {
for (int i = ; i <= ; i++)
System.out.println(i);
}
}
public class TestCountDownLatch {
public static void main(String[] args) {
LatchDemo ld = new LatchDemo();
long start = System.currentTimeMillis();
for (int i = ; i < ; i++)
new Thread(ld).start();
long end = System.currentTimeMillis();
System.out.println("total time is " + (end - start));
}
}
會發現無法達到預期的效果,甚至在輸出的最後一行根本看不到“total time is XXX”的結果,這是正常的,因為在這個多線程的環境下,或許當其他線程還沒有将偶數完全輸出,main線程已經将時間計算完畢并且輸出了。要解決這個問題,我們需要使main線程中計算時間的代碼在其他所有線程運算全部完成之後才執行,這就是CountDownLatch的功能,下面我們使用CountDownLatch來改程序式:
package concurrent;
import java.util.concurrent.CountDownLatch;
class LatchDemo implements Runnable {
private CountDownLatch latch;
public LatchDemo(CountDownLatch latch) {
this.latch = latch;
}
@Override
public void run() {
try {
for (int i = ; i < ; i++)
System.out.println(i);
} finally {
//使用finally確定倒計時操作一定可以執行
latch.countDown();
}
}
}
public class TestCountDownLatch {
public static void main(String[] args) {
//參數5對應要等待的線程數量,我們在下面建立了5個線程
CountDownLatch latch = new CountDownLatch();
LatchDemo ld = new LatchDemo(latch);
long start = System.currentTimeMillis();
for (int i = ; i < ; i++)
new Thread(ld).start();
//等待其他所有線程的運算全部完成
try {
latch.await();
} catch (InterruptedException e) {
e.printStackTrace();
}
long end = System.currentTimeMillis();
System.out.println("total time is " + (end - start));
}
}
運作程式,發現可以正常計算整個程式的執行時間:
