CountDownLatch的用法
CountDownLatch典型用法1
某一线程在开始运行前等待n个线程执行完毕。将CountDownLatch的计数器初始化为n
new CountDownLatch(n) ,每执行一次countdownlatch.countDown()计数器将减1 ,
当计数器的值变为0时,在CountDownLatch上 await() 的线程就会被唤醒。
一个典型应用场景就是启动一个服务时,主线程需要等待多个组件加载完毕,之后再继续执行。
public static void main(String[] args) throws InterruptedException {
CountDownLatch latch = new CountDownLatch(10);
for (int i=0; i<9; i++) {
new Thread(new Runnable() {
@Override
public void run() {
System.out.println(Thread.currentThread().getName() + " 运行");
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
latch.countDown();
}
}
}).start();
}
System.out.println("等待子线程运行结束");
latch.await(10, TimeUnit.SECONDS);
System.out.println("子线程运行结束");
}
CountDownLatch典型用法2
CountDownLatch典型用法2:实现多个线程开始执行任务的最大并行性。注意是并行性,不是并发,强调的是多个线程在某一时刻同时开始执行。类似于赛跑,将多个线程放到起点,等待发令枪响,然后同时开跑。做法是初始化一个共享的CountDownLatch(1),将其计数器初始化为1,多个线程在开始执行任务前首先 coundownlatch.await(),当主线程调用 countDown() 时,计数器变为0,多个线程同时被唤醒。
class MyRunnable implements Runnable {
private CountDownLatch falingqiang;
private CountDownLatch jifenyuan;
public MyRunnable(CountDownLatch falingqiang, CountDownLatch jifenyuan) {
this.falingqiang= falingqiang;
this.jifenyuan= jifenyuan;
}
@Override
public void run() {
try {
falingqiang.await(); //等待发令枪枪响
System.out.println("运动员" +Thread.currentThread().getName()+ "开始跑");
Thread.sleep(1000);
jifenyuan.countDown(); //计分员每记录一个一个运动员 数量减一
} catch (InterruptedException e) {
e.printStackTrace();
}
}
//*********************************************************
public static void main(String[] args) throws InterruptedException {
CountDownLatch falingqiang= new CountDownLatch(1);
CountDownLatch jifenyuan= new CountDownLatch(5);
for (int i=0; i< 5; i++) {
new Thread(new MyRunnable(falingqiang, jifenyuan)).start();
}
System.out.println("比赛前准备");
Thread.sleep(3000);
falingqiang.countDown(); //发令枪响
System.out.println("运动员比赛中");
jifenyuan.await(); //计分员记录完所有的运动员分数
System.out.println("比赛结束");
}