Java 利用JUC CountDownLatch 线程池Executors 实现多线程操作

简介: Java 利用JUC CountDownLatch 线程池Executors 实现多线程操作业务场景:某个业务操作非常耗时,但又必须等这个操作结束后才能进行后续操作

Java 利用JUC CountDownLatch 线程池Executors 实现多线程操作

业务场景:某个业务操作非常耗时,但又必须等这个操作结束后才能进行后续操作

importorg.springframework.util.CollectionUtils;

importjava.util.List;

importjava.util.concurrent.CountDownLatch;

importjava.util.concurrent.ExecutorService;

importjava.util.concurrent.Executors;

importjava.util.concurrent.TimeUnit;

importjava.util.function.Consumer;

importjava.util.stream.Collectors;

importjava.util.stream.Stream;

/**

* 多线程任务处理工具类

* gzh-JavaNice

*/

publicclassTaskDisposeUtils {

   //并行线程数

   publicstaticfinalintPOOL_SIZE;

   static {

       //判断核心线程数 如果机器的核心线程数大于5则用机器核心线程数

       POOL_SIZE=Integer.max(Runtime.getRuntime().availableProcessors(), 5);

   }

   /**

    * 并行处理,并等待结束

    *

    * @param taskList 任务列表

    * @param consumer 消费者

    * @param <T>

    * @throws InterruptedException

    */

   publicstatic<T>voiddispose(List<T>taskList, Consumer<T>consumer) throwsInterruptedException {

       dispose(true, POOL_SIZE, taskList, consumer);

   }

   /**

    * 并行处理,并等待结束

    *

    * @param moreThread 是否多线程执行

    * @param poolSize   线程池大小

    * @param taskList   任务列表

    * @param consumer   消费者

    * @param <T>

    * @throws InterruptedException

    */

   publicstatic<T>voiddispose(booleanmoreThread, intpoolSize, List<T>taskList, Consumer<T>consumer) throwsInterruptedException {

       if (CollectionUtils.isEmpty(taskList)) {

           return;

       }

       //如果是多线程且核心线程数大于一则进入方法

       if (moreThread&&poolSize>1) {

           poolSize=Math.min(poolSize, taskList.size());

           ExecutorServiceexecutorService=null;

           try {

               //新建一个固定大小的线程池 核心线程数为poolSize

               executorService=Executors.newFixedThreadPool(poolSize);

               //juc工具类 用于让必须所有任务都处理完后才进行下一步

               CountDownLatchcountDownLatch=newCountDownLatch(taskList.size());

               for (Titem : taskList) {

                   executorService.execute(() -> {

                       try {

                           //消费任务

                           consumer.accept(item);

                       } finally {

                           //处理完后减一

                           countDownLatch.countDown();

                       }

                   });

               }

               //在此等待 当countDownLatch变成0后才继续进行下一步

               countDownLatch.await();

           } finally {

               if (executorService!=null) {

                   executorService.shutdown();

               }

           }

       } else {

           for (Titem : taskList) {

               consumer.accept(item);

           }

       }

   }

  publicstaticvoidmain(String[] args) throwsInterruptedException {

       //生成1-10的10个数字,放在list中,相当于10个任务

       List<Integer>list=Stream.iterate(1, a->a+1).limit(10).collect(Collectors.toList());

       JSONObjectobject=newJSONObject();

       object.put("name","sss");

       //启动多线程处理list中的数据,每个任务休眠时间为list中的数值

//        Consumer<Integer> c= item -> {

//            try {

//                long startTime = System.currentTimeMillis();

//                object.put("s",item);

//                TimeUnit.SECONDS.sleep(item);

//                long endTime = System.currentTimeMillis();

//                System.out.println(object.toJSONString());

//                System.out.println(System.currentTimeMillis() + ",任务" + item + "执行完毕,耗时:" + (endTime - startTime));

//            } catch (InterruptedException e) {

//                e.printStackTrace();

//            }

//        };

       TaskDisposeUtils.dispose(list, item-> {

           try {

               longstartTime=System.currentTimeMillis();

               object.put("s",item);

               TimeUnit.SECONDS.sleep(item);

               longendTime=System.currentTimeMillis();

               System.out.println(object.toJSONString());

               System.out.println(System.currentTimeMillis() +",任务"+item+"执行完毕,耗时:"+ (endTime-startTime));

           } catch (InterruptedExceptione) {

               e.printStackTrace();

           }

       });

       //上面所有任务处理完毕完毕之后,程序才能继续

       System.out.println(list+"中的任务都处理完毕!");

   }

}

执行结果

🖊️最后总结

🖲要熟练掌握技巧,一定多多坚持练习:骐骥一跃,不能十步;驽马十驾,功在不舍


目录
相关文章
|
10月前
|
Java 开发者
Java并发编程:CountDownLatch实战解析
Java并发编程:CountDownLatch实战解析
628 100
|
安全 算法 Java
Java 多线程:线程安全与同步控制的深度解析
本文介绍了 Java 多线程开发的关键技术,涵盖线程的创建与启动、线程安全问题及其解决方案,包括 synchronized 关键字、原子类和线程间通信机制。通过示例代码讲解了多线程编程中的常见问题与优化方法,帮助开发者提升程序性能与稳定性。
473 0
|
机器学习/深度学习 消息中间件 存储
【高薪程序员必看】万字长文拆解Java并发编程!(9-2):并发工具-线程池
🌟 ​大家好,我是摘星!​ 🌟今天为大家带来的是并发编程中的强力并发工具-线程池,废话不多说让我们直接开始。
450 0
|
9月前
|
缓存 安全 Java
JUC系列之《CountDownLatch:同步多线程的精准发令枪 》
CountDownLatch是Java并发编程中用于线程协调的同步工具,通过计数器实现等待机制。主线程等待多个工作线程完成任务后再继续执行,适用于资源初始化、高并发模拟等场景,具有高效、灵活、线程安全的特点,是JUC包中实用的核心组件之一。
|
9月前
|
设计模式 缓存 安全
【JUC】(6)带你了解共享模型之 享元和不可变 模型并初步带你了解并发工具 线程池Pool,文章内还有饥饿问题、设计模式之工作线程的解决于实现
JUC专栏第六篇,本文带你了解两个共享模型:享元和不可变 模型,并初步带你了解并发工具 线程池Pool,文章中还有解决饥饿问题、设计模式之工作线程的实现
597 2
|
9月前
|
Java 测试技术 API
【JUC】(1)带你重新认识进程与线程!!让你深层次了解线程运行的睡眠与打断!!
JUC是什么?你可以说它就是研究Java方面的并发过程。本篇是JUC专栏的第一章!带你了解并行与并发、线程与程序、线程的启动与休眠、打断和等待!全是干货!快快快!
1216 2
|
9月前
|
设计模式 消息中间件 安全
【JUC】(3)常见的设计模式概念分析与多把锁使用场景!!理解线程状态转换条件!带你深入JUC!!文章全程笔记干货!!
JUC专栏第三篇,带你继续深入JUC! 本篇文章涵盖内容:保护性暂停、生产者与消费者、Park&unPark、线程转换条件、多把锁情况分析、可重入锁、顺序控制 笔记共享!!文章全程干货!
457 1
|
12月前
|
数据采集 监控 调度
干货分享“用 多线程 爬取数据”:单线程 + 协程的效率反超 3 倍,这才是 Python 异步的正确打开方式
在 Python 爬虫中,多线程因 GIL 和切换开销效率低下,而协程通过用户态调度实现高并发,大幅提升爬取效率。本文详解协程原理、实战对比多线程性能,并提供最佳实践,助你掌握异步爬虫核心技术。
|
Java 数据挖掘 调度
Java 多线程创建零基础入门新手指南:从零开始全面学习多线程创建方法
本文从零基础角度出发,深入浅出地讲解Java多线程的创建方式。内容涵盖继承`Thread`类、实现`Runnable`接口、使用`Callable`和`Future`接口以及线程池的创建与管理等核心知识点。通过代码示例与应用场景分析,帮助读者理解每种方式的特点及适用场景,理论结合实践,轻松掌握Java多线程编程 essentials。
844 5
|
监控 搜索推荐 Java
Java 多线程最新实操技术与应用场景全解析:从基础到进阶
本文深入探讨了Java多线程的现代并发编程技术,涵盖Java 8+新特性,如CompletableFuture异步处理、Stream并行流操作,以及Reactive编程中的Reactor框架。通过具体代码示例,讲解了异步任务组合、并行流优化及响应式编程的核心概念(Flux与Mono)。同时对比了同步、CompletableFuture和Reactor三种实现方式的性能,并总结了最佳实践,帮助开发者构建高效、扩展性强的应用。资源地址:[点击下载](https://pan.quark.cn/s/14fcf913bae6)。
634 3

热门文章

最新文章