线程池中的栅栏

当前位置:首页易利备用手机版 >

易利备用手机版

线程池中的栅栏

时间:2019-06-10本站浏览次数:148

       

多线程中有三个类,分别是CountDownLatch,CyclicBarrier,Semaphore。代表着线程中的栅栏。共享锁。

CountDownLatch

在一组线程中,一个线程等待其他线程。我把它理解为门栓。

查看该类的数据结构图如下图一

​ 图一

有一个静态的内部类,Sync继承自AQS。

CountDownLatch(int) : 有参构造方法,该类拥有的共享锁次数。await() : 阻塞,等待该类释放掉共享锁,也就是说,拥有共享锁的次数为0countDown:释放一次共享锁getCount: 获取共享锁次数

使用例子:代码如下:

/** * @ClassName CountDownLatchTest * @Description 共享锁。在完成一组正在其他线程中执行的操作之前,允许一个或者多个线程一直等待 * @Author ouyangkang * @Date 2018/10/23 14:33 **/public class CountDownLatchTest { private static int SIZE = 6; private static CountDownLatch countDownLatch; /** * @Date 2018/10/25 15:49 * @Description 阻塞队列为3 核心池的大小为2 最大池的大小为6的线程池 **/ private static ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor( 2, 6, 60L,TimeUnit.SECONDS, new LinkedBlockingDeque<>(3)); public static void main(String[] args) { countDownLatch = new CountDownLatch(SIZE); for (int i = 0; i < 6; i++) { threadPoolExecutor.execute(new ThreadTest()); } try { // 阻塞等待 countDownLatch.await(); System.out.printf("thread main = [{%s}] ", Thread.currentThread().getName()); threadPoolExecutor.shutdown(); } catch (InterruptedException e) { e.printStackTrace(); } } static class ThreadTest extends Thread { @Override public void run() { System.out.printf("thread-name = [%s] ", Thread.currentThread().getName()); try { Thread.sleep(10000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.printf("thread-name =[%s] 执行 ", Thread.currentThread().getName()); // 数值减一 countDownLatch.countDown(); } }}

返回结果:

thread-name = [pool-1-thread-1] thread-name = [pool-1-thread-3] thread-name = [pool-1-thread-2] thread-name =[pool-1-thread-1] 执行 thread-name =[pool-1-thread-3] 执行 thread-name = [pool-1-thread-1] thread-name = [pool-1-thread-3] thread-name =[pool-1-thread-2] 执行 thread-name = [pool-1-thread-2] thread-name =[pool-1-thread-1] 执行 thread-name =[pool-1-thread-3] 执行 thread-name =[pool-1-thread-2] 执行 thread main = [{main}] 线程池中阻塞队列为3,启动了6个线程。阻塞队列中阻塞3个,核心池2个在执行任务,最大池的大小为6,那么就会新建一个线程来处理该任务。主线程最后执行,wait等待其他线程任务执行完毕,再继续执行主线程。

CyclicBarrier

在一组线程中允许多个线程相互等待。就是,每个线程都先执行一下,然后互相等待到一个点。然后再执行。

查看该类的数据结构图

有参构造方法,设置屏障点是多少,创建线程,等待。直到线程数量大于等于该屏障点。处于该屏障点等待得线程全部唤醒。

使用例子如下:

/** * @ClassName CyclicBarrierTest * @Description 屏障,允许多个线程相互等待。到达了某一个临界点,就唤醒所有线程 * @Author ouyangkang * @Date 2018/10/23 15:00 **/public class CyclicBarrierTest { private static int SIZE = 5; private static CyclicBarrier cyclicBarrier; public static void main(String[] args) { cyclicBarrier = new CyclicBarrier(SIZE); for (int i = 0; i < 5 ;i++){ new ThreadTest().start(); } } static class ThreadTest extends Thread { @Override public void run() { System.out.printf("thread=[%s] 开始-- ", Thread.currentThread().getName()); try { Thread.sleep(1000); cyclicBarrier.await(); System.out.printf("thread=[%s] 继续--- ", Thread.currentThread().getName()); } catch (InterruptedException e) { e.printStackTrace(); } catch (BrokenBarrierException e) { e.printStackTrace(); } } }}

结果如下:

thread=[Thread-0] 开始-- thread=[Thread-4] 开始-- thread=[Thread-3] 开始-- thread=[Thread-1] 开始-- thread=[Thread-2] 开始-- thread=[Thread-2] 继续--- thread=[Thread-4] 继续--- thread=[Thread-0] 继续--- thread=[Thread-1] 继续--- thread=[Thread-3] 继续---

Semaphore

在一组线程中,线程持有信号量,如果信息量得大小为10,那么所有线程能够持有得信号量不能超过10,如果3个线程分别持有得信号量是3 4 5 。 那么只能是两个线程运行,当其中一个释放了该信号量,其他线程才可以运行。

类图结构如下:

具体例子如下:

/** * @ClassName SemaphoreTest * @Description 信号量 * @Author ouyangkang * @Date 2018/10/23 16:34 **/public class SemaphoreTest { private static int SIZE = 10; public static void main(String[] args) { Semaphore semaphore = new Semaphore(SIZE); ExecutorService executorService = new ThreadPoolExecutor(2,3,60L,TimeUnit.SECONDS,new LinkedBlockingQueue<>(5)); executorService.execute(new ThreadTest(3,semaphore)); executorService.execute(new ThreadTest(4,semaphore)); executorService.execute(new ThreadTest(5,semaphore)); executorService.shutdown(); } static class ThreadTest extends Thread{ private Integer count ; private Semaphore semaphore; public ThreadTest(Integer count , Semaphore semaphore){ this.count = count ; this.semaphore = semaphore; } @Override public void run() { try { semaphore.acquire(count); System.out.printf("thread=[%s] 拥有信号量 semaphore=[%d] 开始---- ",Thread.currentThread().getName(), count); Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); }finally { semaphore.release(count); System.out.printf("thread=[%s] 释放了 semaphore=[%d] --",Thread.currentThread().getName(),count); } } }}

具体结果如下:

thread=[pool-1-thread-2] 拥有信号量 semaphore=[4] 开始---- thread=[pool-1-thread-1] 拥有信号量 semaphore=[3] 开始---- thread=[pool-1-thread-2] 释放了 semaphore=[4] --thread=[pool-1-thread-2] 拥有信号量 semaphore=[5] 开始---- thread=[pool-1-thread-1] 释放了 semaphore=[3] --thread=[pool-1-thread-2] 释放了 semaphore=[5] --, 1, 0, 9);




公司地址:浙江杭州余杭区
联系人:翁华国 13908354804
王云鹏 15293455901
电话:18800671035 传真:13u6n4@163.com
邮箱:522ihld@hotmail.com

粤公网安备 44030702001579号

易利go代理几个点@