登录
首页 >  文章 >  java教程

Java多线程协作作业之信号同步怎么实现

来源:亿速云

时间:2024-04-22 21:33:29 276浏览 收藏

本篇文章主要是结合我之前面试的各种经历和实战开发中遇到的问题解决经验整理的,希望这篇《Java多线程协作作业之信号同步怎么实现》对你有很大帮助!欢迎收藏,分享给更多的需要的朋友学习~

    一、信号同步

    多线程很多时候是协作作业。比如4个线程对电商数据分季度统计,统计完成之后,再汇总。如何知道4个线程都执行完成呢,我们可以使用JDK1.5给我们提供的辅助类CountDownLatch(

    减少计数)、CyclicBarrier(循环栅栏)、Semaphore(信号灯)。

    二、基于时间维度

    1、CountDownLatch

    多少个协作线程就初始化CountDownLatch的构造参数是多少。

     public static void main(String[] args) throws InterruptedException {
            final int NUM=6;
            //定义总数量;
            CountDownLatch countDownLatch=new CountDownLatch(NUM);
            for (int i = 0; i < NUM; i++) {
                new Thread(()->{
                    System.out.println(Thread.currentThread().getName()+"线程,已执行!");
                    //减少计数
                    countDownLatch.countDown();
                },String.valueOf(i+1)).start();
            }
            //等待所有任务完成
            countDownLatch.await();
            System.out.println("所有线程任务已经执行完成!");
        }

    Java多线程协作作业之信号同步怎么实现

    2、CyclicBarrier

    与减少计数类似

     public static void main(String[] args) {
            final int NUM = 6;
            //定义循环数量及循环完成后的任务(Runnable接口实现);
            CyclicBarrier cyclicBarrier = new CyclicBarrier(NUM, () -> {
                System.out.println("所有线程任务已经执行完成!");
            });
            for (int i = 0; i < NUM; i++) {
                new Thread(()->{
                    System.out.println(Thread.currentThread().getName()+"线程,已执行!");
                    try {
                        //等待点或障碍点,等待所有任务完成,
                        cyclicBarrier.await();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    } catch (BrokenBarrierException e) {
                        e.printStackTrace();
                    }
                },String.valueOf(i+1)).start();
            }
        }

    Java多线程协作作业之信号同步怎么实现

    三、基于信号维度

    Semaphore,线程与信号是m:n,其中m>=n。

    import java.util.Random;
    import java.util.concurrent.Semaphore;
    import java.util.concurrent.TimeUnit;
    /*信号灯
    * 6个线程,抢占三个信号
    * */
    public class SemaphoreDemo {
        public static void main(String[] args) {
            Semaphore semaphore=new Semaphore(3);
            for (int i = 0; i < 6; i++) {
                new Thread(()->{
                    try {
                        //获取信号
                        semaphore.acquire();
                        System.out.println("线程:"+Thread.currentThread().getName()+"----获取信号");
                        int time = new Random().nextInt(5);
                        System.out.println(("线程:"+Thread.currentThread().getName()+"----休眠"+time+"s!"));
                        TimeUnit.SECONDS.sleep(time);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }finally {
                    //    释放信号
                        System.out.println("线程:"+Thread.currentThread().getName()+"---释放信号");
                        semaphore.release();
                    }
                },String.valueOf(i+1)).start();
            }
        }
    }

    首先线程4、1、3获取到信号,线程1释放信号后,线程2获得信号。线程2、3释放信号后,线程5、6获得信号。

    Java多线程协作作业之信号同步怎么实现

    好了,本文到此结束,带大家了解了《Java多线程协作作业之信号同步怎么实现》,希望本文对你有所帮助!关注golang学习网公众号,给大家分享更多文章知识!

    声明:本文转载于:亿速云 如有侵犯,请联系study_golang@163.com删除
    相关阅读
    更多>
    最新阅读
    更多>
    课程推荐
    更多>