当前位置: 首页 > news >正文

Java并发编程中的CountDownLatch与CompletableFuture:同步与异步的完美搭档

引言

在Java并发编程中,CountDownLatchCompletableFuture是两个常用于多线程协作的重要工具。它们分别针对不同的场景提供了高效的解决方案:

  • CountDownLatch 是一个同步工具,用于等待一组线程完成特定操作后再继续执行。
  • CompletableFuture 是一个异步编程框架,支持异步任务的链式调用、结果处理和任务组合。

本文将深入解析这两个工具的核心功能、使用场景以及它们之间的区别,并通过代码示例帮助读者掌握实际应用技巧。


1. CountDownLatch:同步的基石

1.1 核心功能

CountDownLatch(倒计时门闩)通过一个计数器实现线程同步。

  • 初始化:指定一个初始计数值(例如 new CountDownLatch(3))。
  • countDown():每调用一次,计数器减1。
  • await():阻塞当前线程,直到计数器为0。
1.2 使用场景
  • 等待多个线程完成任务:例如主线程需要等待多个子线程完成计算后再汇总结果。
  • 资源初始化同步:确保所有资源加载完成后,再启动业务逻辑。
1.3 代码示例
import java.util.concurrent.CountDownLatch;public class CountDownLatchExample {public static void main(String[] args) throws InterruptedException {int threadCount = 3;CountDownLatch latch = new CountDownLatch(threadCount);for (int i = 0; i < threadCount; i++) {new Thread(() -> {try {System.out.println(Thread.currentThread().getName() + " 正在执行任务");Thread.sleep(1000); // 模拟任务耗时} finally {latch.countDown(); // 计数器减1}}).start();}System.out.println("主线程等待所有子线程完成...");latch.await(); // 阻塞直到计数器为0System.out.println("所有子线程已完成,主线程继续执行");}
}

输出结果

主线程等待所有子线程完成...
Thread-0 正在执行任务
Thread-1 正在执行任务
Thread-2 正在执行任务
所有子线程已完成,主线程继续执行

2. CompletableFuture:异步编程的瑞士军刀

2.1 核心功能

CompletableFuture 是 Java 8 引入的异步编程工具,支持以下特性:

  • 异步任务执行:通过 runAsync 或 supplyAsync 启动异步任务。
  • 链式调用:通过 thenApplythenAccept 等方法处理结果或执行后续操作。
  • 任务组合:通过 allOfanyOf 等方法组合多个异步任务。
2.2 使用场景
  • 异步任务链式处理:例如先下载文件,再解析内容,最后保存到数据库。
  • 并行任务聚合:同时执行多个独立任务,并等待所有结果。
  • 异常处理:通过 exceptionally 或 handle 方法捕获异步任务中的异常。
2.3 代码示例
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;public class CompletableFutureExample {public static void main(String[] args) {ExecutorService executor = Executors.newFixedThreadPool(2);CompletableFuture<Void> future = CompletableFuture.runAsync(() -> {System.out.println("异步任务1执行");}, executor).thenRunAsync(() -> {System.out.println("异步任务2执行");}, executor);future.join(); // 等待所有异步任务完成executor.shutdown();}
}

输出结果

异步任务1执行
异步任务2执行

3. CountDownLatch vs CompletableFuture

特性CountDownLatchCompletableFuture
功能简单的同步工具丰富的异步编程框架
使用难度简单复杂(需学习链式调用和组合方法)
适用场景单纯等待多个线程完成异步任务链式处理、结果组合、异常处理等
是否支持结果返回是(通过 supplyAsync 和回调函数)
是否支持异常处理是(通过 exceptionally 或 handle

4. 实际应用建议

4.1 如何选择工具?
  • 使用 CountDownLatch 的场景

    • 需要等待一组线程完成任务,但无需获取任务结果。
    • 示例:等待多个线程初始化共享资源后,再启动主流程。
  • 使用 CompletableFuture 的场景

    • 需要异步执行任务,并处理任务结果或组合多个任务。
    • 示例:并行下载多个文件后合并内容,或执行一系列依赖的异步操作。
4.2 结合使用示例
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;public class HybridExample {public static void main(String[] args) throws InterruptedException {CountDownLatch latch = new CountDownLatch(2);ExecutorService executor = Executors.newFixedThreadPool(2);CompletableFuture<Void> future1 = CompletableFuture.runAsync(() -> {System.out.println("异步任务1执行");latch.countDown();}, executor);CompletableFuture<Void> future2 = CompletableFuture.runAsync(() -> {System.out.println("异步任务2执行");latch.countDown();}, executor);latch.await(); // 等待两个异步任务完成System.out.println("所有异步任务已完成");executor.shutdown();}
}

5. 总结

  • CountDownLatch 是同步工具的代表,适用于简单的线程等待场景。
  • CompletableFuture 是异步编程的利器,支持复杂的任务组合和结果处理。
  • 在实际开发中,根据需求选择合适的工具:
    • 简单同步 → CountDownLatch
    • 异步任务链式处理 → CompletableFuture

通过合理使用这两个工具,可以显著提升多线程程序的性能和可维护性。无论是构建高并发的服务器,还是优化异步任务流程,它们都是不可或缺的“瑞士军刀”!


文章转载自:

http://cSkYyIIy.dqggd.cn
http://Q1nvsBhN.dqggd.cn
http://ir5vSRFT.dqggd.cn
http://rA9vLteb.dqggd.cn
http://KvKnNjs8.dqggd.cn
http://bEim8a2z.dqggd.cn
http://vw7EdaEI.dqggd.cn
http://AK1sUhou.dqggd.cn
http://wVAyaSyA.dqggd.cn
http://on3p4ybN.dqggd.cn
http://28FRrA5s.dqggd.cn
http://H3E44cF7.dqggd.cn
http://01Fd46yn.dqggd.cn
http://4UAHQojZ.dqggd.cn
http://2DDVlz6L.dqggd.cn
http://wQSvo1XL.dqggd.cn
http://inLDdpyE.dqggd.cn
http://RAHDZ0CA.dqggd.cn
http://GMKf0w3G.dqggd.cn
http://ateiwQks.dqggd.cn
http://M0uQouAf.dqggd.cn
http://IjfgpEYz.dqggd.cn
http://YLn9xdyq.dqggd.cn
http://ARcDXThH.dqggd.cn
http://hDwQjKUp.dqggd.cn
http://MgoG0ZLF.dqggd.cn
http://2pOlmAz0.dqggd.cn
http://tc9TrA7H.dqggd.cn
http://9cx6ZjjM.dqggd.cn
http://9tJWmho2.dqggd.cn
http://www.dtcms.com/a/365959.html

相关文章:

  • 驱动增长的双引擎:付费搜索与自然搜索的终极平衡策略
  • Loot模板系统
  • helm应该安装在哪些节点
  • ABAQUS多尺度纤维增强混凝土二维建模
  • 微信小程序-day3
  • 【mac】macOS上的实用Log用法
  • 使用Navicat去批量传输数据库的表结构
  • fastlio配置与过程中遇到的问题
  • 51单片机----LED与数码管模块
  • C 语言标准输入输出库:`stdio.h` 的使用详解
  • 【WPS】WPSPPT 快速抠背景
  • Python学习笔记--使用Django修改和删除数据
  • 52.【.NET8 实战--孢子记账--从单体到微服务--转向微服务】--解决客户端调用接口404问题
  • 硬件:51单片机的按键、中断、定时器、PWM及蜂鸣器
  • Spring Boot HTTP状态码详解
  • 性能测试-jmeter8-脚本录制
  • 揭秘23种设计模式的艺术与技巧
  • < 自用文 主机 USC 记录:> 发现正在被攻击 后的自救
  • Protocol Buffers:数据世界的秘语之书,手把手教学环境搭建
  • mysql高级进阶(存储过程)
  • 认识HTML
  • CDN的工作原理是什么?为什么要用高防 CDN?
  • 数据结构:双向链表
  • 分割回文串手绘图
  • 电脑城老板不会告诉你的装机秘籍:建造者模式让你的代码高配起飞!
  • @Autowired原理(三)
  • 【Qt中信号槽连接connect有接收者和无接收者的区别】
  • LeetCode 20.有效的符号算法解析及栈的相关知识
  • FTL文件格式的原理与应用(AI)
  • 【工具变量】上市公司绿色供应链管理示范企业DID数据(2010-2024年)