背景
最近宅家办公,效率低下,总觉得有点失落,哪里也去不了,无奈只能写一篇博客来发泄发泄。刚好最近在优化代码,有个功能需要同时调用三个外部接口,看旧代码是三次调用顺序执行,每次调用超时3s,如果遇到网络渣的情况,整体调用时间可能超过9s,还有很大的压榨价值啊!
刚好最近在学多线程,利用学过的一点知识小试牛刀,也不失为人生的一大快事啊!
CountDownLatch
CountDownLatch是一个计数器,当计数器的值大于0时,执行等待方法await,阻塞直到计数器的值等于0时,才放行。
Lach有门闩的意思,可以把它理解成一道栅栏,举个生活中的例子,运动员在起跑线上,等待发号员口令,这是运动员调用的是await方法。发号员数"3、2、1“时,调用了三次downCount方法。当值为0时,运动员就开跑。
案例
《教父》是我最喜欢的电影之一,情节曲折生动,主演演技炸裂。教父迈克尔克里昂正执行他的复仇计划,需要派他的小弟去干五大家族的首领,他不可能只叫一个人去吧,一是效率低,二是留了充分时间让对手有所防范。于是,他派了五大杀手在同一时刻去刺杀五大首领
代码和注释
private static final CountDownLatch countDownLatch = new CountDownLatch(5);
private static List<String> bossList = new ArrayList<>();
public static void main(String[] args) throws InterruptedException {
new AssassinateThread("杀手一", "吉诺维斯家族首领").start();
new AssassinateThread("杀手二", "波纳诺家族首领").start();
new AssassinateThread("杀手三", "科洛博家族首领").start();
new AssassinateThread("杀手四", "卢凯塞家族首领").start();
new AssassinateThread("杀手五", "甘比诺家族首领").start();
countDownLatch.await();
// 执行到这里,理论上全部首领刺杀成功
System.out.println("刺杀成功名单:");
for (String bossName : bossList) {
System.out.print(bossName + " ");
}
}
private static class AssassinateThread extends Thread {
private String bossName;
public AssassinateThread(String name, String bossName) {
super(name);
this.bossName = bossName;
}
@Override
public void run() {
bossList.add(bossName);
countDownLatch.countDown(); // 计数器减一
}
}