zoukankan      html  css  js  c++  java
  • 多线程-闭锁CountDownLatch

      闭锁相当于相当于一扇门,在闭锁到达结束状态之前,这扇门一直是关着的,所有的线程都不可以通过。它可以使一个或者一组线程等待某个时间发生。闭锁状态包括一个计数器,初始化的时候传入一个正数,这个数字表示等待的事件的个数。countDown方法递减计数器,表示一个事件已经发生。如果计数器的值为非0,await方法会一直阻塞到计数器为0。当计数器为0,表示等待的事件已经发生,这时候所有的线程才可以继续往下执行。

      闭锁的实现有CountDownLatch,类似于我们生活的田径比赛,当运动员听到裁判员的哨声时,运动员才可以开始跑,未听到裁判的哨声运动员不可以跑。这个时候不管所有的运动员是否已经准备就绪了,只要哨声一响,就可以跑。这个跟后面的栅栏有区别,运动员只等待一个事件,就是听到裁判员的哨声响起。下面看一下实现的代码,如下:

    package countDownLatch.countDownLatch;
    
    import java.util.concurrent.CountDownLatch;
    import java.util.concurrent.ExecutorService;
    import java.util.concurrent.Executors;
    
    public class CountDownLatchDemo {
    
        public static void main(String[]args) throws InterruptedException{
            final CountDownLatch startGate=new CountDownLatch(1);
            final CountDownLatch endGate=new CountDownLatch(5);
            //线程池
            ExecutorService exce=Executors.newCachedThreadPool();
            //创建5个线程
            for(int i=1;i<=5;i++){
                final int num=i;
                Thread thread =new Thread(new Runnable() {
                    public void run() {
                        try {
                            System.out.println(num+"号选手准备就绪,等待裁判员哨声响起..");
                            //相当于同步锁Synchronized中的await()方法
                            startGate.await();
                            try {
                                Thread.sleep((long) (Math.random()*10000));
                            } catch (InterruptedException e) {
                                e.printStackTrace();
                            }
                            System.out.println(num+"号选手到达终点..");
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        finally{
                            //相当于同步锁Synchronized中的notify()方法,区别在于countDown需要执行5次后才能唤醒await()
                            endGate.countDown();
                        }
                    }
                });
                exce.execute(thread);
            }
            long start=System.nanoTime();
            System.out.println("裁判员哨声响起..");
            Thread.sleep(10000);
            //唤醒执行startGate.await()的线程,让线程往下执行
            startGate.countDown();
            //等待被唤醒,主程序才能继续往下执行,线程中每次执行endGate.countDown()就减1,当为零的时候,主程序往下执行
            endGate.await();
            long end=System.nanoTime();
            System.out.println("所有运动员到达终点,耗时:"+(end-start));
            //关闭线程池
            exce.shutdown();
        }
    }

      执行结果如下:

      

       参考地址:JAVA并发编程实战

            http://m.jb51.net/article/63973.htm

  • 相关阅读:
    linux /dev 常见特殊设备介绍与应用[loop,null,zero,full,random]
    由web程序出现乱码开始挖掘(Bom头、字符集与乱码)
    linux shell命令快捷获得系统帮助(一)[manpages定义规范]
    定期分割tomcat输出文件 catalina.out
    readyState的五种状态
    C# FileSystemWatcher
    不用第三个变量实现a,b的值交换
    我的eWork,我能赚钱的SOHO空间
    如何网上炒股
    没有为扩展名“.html”注册的生成提供程序
  • 原文地址:https://www.cnblogs.com/gdpuzxs/p/6993260.html
Copyright © 2011-2022 走看看