来自: http://blog.csdn.net//chenleixing/article/details/42173593 CountDownLatch类是一个同步计数器,构造时传入int参数,该参数就是计数器的初始值,每调用一次countDown()方法,计数器减1,计数器大于0 时,await()方法会阻塞程序继续执行。CountDownLatch可以看作是一个倒计数的锁存器,当计数减至0时触发特定的事件。利用这种特性,可以让主线程等待子线程的结束。下面以一个模拟运动员比赛的例子加以说明。 CountDownLatch的一个非常典型的应用场景是:有一个任务想要往下执行,但必须要等到其他的任务执行完毕后才可以继续往下执行。假如我们这个想要继续往下执行的任务调用一个CountDownLatch对象的await()方法,其他的任务执行完自己的任务后调用同一个CountDownLatch对象上的countDown()方法,这个调用await()方法的任务将一直阻塞等待,直到这个CountDownLatch对象的计数值减到0为止。 1 import java.util.concurrent.CountDownLatch;2 import java.util.concurrent.Executor; 3 import java.util.concurrent.ExecutorService; 4 import java.util.concurrent.Executors; 5 6 public class CountDownLatchDemo { 7 private static final int PLAYER_AMOUNT = 5 ; 8 public CountDownLatchDemo() { 9 // TODO Auto-generated constructor stub 10 } 11 /** 12 * @param args 13 */ 14 public static void main(String[] args) { 15 // TODO Auto-generated method stub 16 // 对于每位运动员,CountDownLatch减1后即结束比赛 17 CountDownLatch begin = new CountDownLatch( 1 ); 18 // 对于整个比赛,所有运动员结束后才算结束 19 CountDownLatch end = new CountDownLatch(PLAYER_AMOUNT); 20 Player[] plays = new Player[PLAYER_AMOUNT]; 21 22 for ( int i = 0 ;i < PLAYER_AMOUNT;i ++ ) 23 plays[i] = new Player(i + 1 ,begin,end); 24 25 // 设置特定的线程池,大小为5 26 ExecutorService exe = Executors.newFixedThreadPool(PLAYER_AMOUNT); 27 for (Player p:plays) 28 exe.execute(p); // 分配线程 29 System.out.println( " Race begins! " ); 30 begin.countDown(); 31 try { 32 end.wait(); // 等待end状态变为0,即为比赛结束 33 } catch (InterruptedException e) { 34 // TODO: handle exception 35 e.printStackTrace(); 36 } finally { 37 System.out.println( " Race ends! " ); 38 } 39 exe.shutdown(); 40 } 41 } ![]() 接下来是Player类 注:countDown最好是在finally里面调用 ![]() 2 3 4 public class Player implements Runnable { 5 6 private int id; 7 private CountDownLatch begin; 8 private CountDownLatch end; 9 public Player( int i, CountDownLatch begin, CountDownLatch end) { 10 // TODO Auto-generated constructor stub 11 super (); 12 this .id = i; 13 this .begin = begin; 14 this .end = end; 15 } 16 17 @Override 18 public void run() { 19 // TODO Auto-generated method stub 20 try { 21 begin.await(); // 等待begin的状态为0 22 Thread.sleep(( long )(Math.random() * 100 )); // 随机分配时间,即运动员完成时间 23 System.out.println( " Play " + id + " arrived. " ); 24 } catch (InterruptedException e) { 25 // TODO: handle exception 26 e.printStackTrace(); 27 } finally { 28 end.countDown(); // 使end状态减1,最终减至0 29 } 30 } 31 } ![]() 下面是张孝祥老师所举例子的程序代码和运行结果: import java.util.concurrent.CountDownLatch; public class CountDownLatchTest { 线程pool-1-thread-1正准备接受命令 |
小黑屋|在路上
( 蜀ICP备15035742号-1 )
GMT+8, 2025-5-4 01:46
Copyright 2015-2025 djqfx