java 倒计时门栓,CountDownLatch 使用详解

1. CountDownLatch 是什么?

从这个类的字面意思来入手,CountDown 是倒计时的意思,Latch 是门栓的意思,加起来的意思就是一个倒计时的门栓。

它其实是作用于线程当中的,它就像一个门栓,一开始是关闭的,所有希望通过该门的线程都需要等待,然后开始倒计时,当倒计时一到,等待的所有线程都可以通过。

要注意的是,它是一次性的,打开之后就不能关上了。

2. 怎么使用 CountDownLatch

2.1 构造方法

public CountDownLatch(int count)

解释:

count 就是需要等待的线程数量

2.2 重要方法

// 调用此方法的线程会被阻塞,直到 CountDownLatch 的 count 为 0

public void await() throws InterruptedException

// 和上面的 await() 作用基本一致,只是可以设置一个最长等待时间

public boolean await(long timeout, TimeUnit unit) throws InterruptedException

// 会将 count 减 1,直至为 0

public void countDown()

2.3 基本使用

2.3.1 需求

现在实现主线程等待其他线程的任务完成之后,才继续执行的代码。

2.3.2 代码实现

public class CountDownLatchDemo {

static class TaskThread extends Thread {

CountDownLatch latch;

public TaskThread(CountDownLatch latch) {

this.latch = latch;

}

@Override

public void run() {

try {

Thread.sleep(1000);

} catch (InterruptedException e) {

e.printStackTrace();

} finally {

System.out.println(getName() + " Task is Done");

latch.countDown();

}

}

}

public static void main(String[] args) throws InterruptedException {

int threadNum = 10;

CountDownLatch latch = new CountDownLatch(threadNum);

for(int i = 0; i < threadNum; i++) {

TaskThread task = new TaskThread(latch);

task.start();

}

System.out.println("Task Start!");

latch.await();

System.out.println("All Task is Done!");

}

}

代码解释:

设置 CountDownLatch 的等待线程数为 10

开启 10 个线程,每个线程都会睡眠 1 秒,睡眠结束后就会调用 CountDownLatch 的 countDown() 方法

主线程调用 CountDownLatch 的 await() 方法,所以会开始阻塞,直到 CountDownLatch 的 count 为 0 才继续执行

打印结果:

Task Start!

Thread-1 Task is Done

Thread-5 Task is Done

Thread-8 Task is Done

Thread-9 Task is Done

Thread-2 Task is Done

Thread-7 Task is Done

Thread-6 Task is Done

Thread-4 Task is Done

Thread-3 Task is Done

Thread-0 Task is Done

All Task is Done!

3. CountDownLatch 使用场景

3.1 同时启动多个线程

如果想同时启动多个线程,实现最大的并行性,就可以使用 CountDownLatch。稍微修改上面的例子代码,代码如下:

public class CountDownLatchDemo {

static class TaskThread extends Thread {

CountDownLatch latch;

public TaskThread(CountDownLatch latch) {

this.latch = latch;

}

@Override

public void run() {

try {

latch.await();

System.out.println(getName() + " start " + System.currentTimeMillis());

} catch (InterruptedException e) {

e.printStackTrace();

}

}

}

public static void main(String[] args) throws InterruptedException {

int threadNum = 10;

CountDownLatch latch = new CountDownLatch(1);

for(int i = 0; i < threadNum; i++) {

TaskThread task = new TaskThread(latch);

task.start();

}

Thread.sleep(1000);

latch.countDown();

}

}

代码解释:

设置 CountDownLatch 等待线程数为 1

开启 10 个线程,每个线程都会调用 CountDownLatch 的 await() 方法,这样每个线程都会被阻塞

主线程休眠 1 秒后,调用 CountDownLatch 的 countDown() 方法,调用后就会唤醒所有等待的线程,所有等待的线程就会同时执行

打印结果:

Thread-1 start 1535987605552

Thread-3 start 1535987605552

Thread-2 start 1535987605552

Thread-0 start 1535987605552

Thread-6 start 1535987605552

Thread-5 start 1535987605552

Thread-8 start 1535987605552

Thread-4 start 1535987605552

Thread-9 start 1535987605552

Thread-7 start 1535987605552

3.2 等待多个线程完成各自任务后再开始执行自己的任务

这个例子在 2.3 节已经说过了,这里就不再细说了。

参考文章:

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值