多线程系列之十一:Two-Phase Termination模式
一,Two-Phase Termination模式
翻译过来就是:分两阶段终止
二,示例程序
public class CountupTread extends Thread {
    private long counter = 0;
    private volatile  boolean shutdownRequested = false;
    //中止请求
    public void shutdownRequest(){
        shutdownRequested = true;
        interrupt();//中断所有等待队列中的线程
    }
    //检查是否发出了终止请求
    public boolean isShutdownRequested(){
        return shutdownRequested;
    }
    //线程体
    @Override
    public void run() {
        try {
            while (!isShutdownRequested()){
                doWork();
            }
        }catch (InterruptedException e){
        }finally {
            doShutdown();
        }
    }
    //终止处理
    private void doShutdown() {
        System.out.println("doShutdown:counter = "+counter);
    }
    //正常操作
    private void doWork()throws InterruptedException {
        counter++;
        System.out.println("doWork :counter = "+counter);
            Thread.sleep(500);
    }
}
public class Test {
    public static void main(String[] args) {
        System.out.println( " main : begin ");
        try {
            //启动线程
            CountupTread t = new CountupTread();
            t.start();
            //模拟处理业务
            Thread.sleep(10000);
            //线程的终止请求
            System.out.println(" main shutdownRequest");
            t.shutdownRequest();
            System.out.println(" main : join");
            //等待线程终止
            t.join();
        }catch (InterruptedException e){
        }
        System.out.println( " main : end ");
    }
}
三,特点
安全地终止线程
必定会进行终止处理
发出终止请求后尽快进行终止处理
四,java.util.cocurrent包与线程同步
1.CountDownLatch类
public class CountdownLatchTest {
    public static void main(String[] args) {
        ExecutorService executorService = Executors.newCachedThreadPool();
        final CountDownLatch cdOrder = new CountDownLatch(1);
        final CountDownLatch cdAnswer = new CountDownLatch(3);
        for (int i = 0; i < 3; i++) {
            Runnable runnable = new Runnable() {
                @Override
                public void run() {
                    try {
                        System.out.println("线程"+Thread.currentThread().getName()+"正准备接受命令");
                        //cdOrder的初始值为1,当线程执行到cdOrder.await();会阻塞在这里。
                        // 当执行了cdOrder.countDown();会减为0,一旦为0,就开始继续执行
                        cdOrder.await();
                        System.out.println("线程"+Thread.currentThread().getName()+"已经接受命令");
                        Thread.sleep((long) (Math.random()*10000));
                        System.out.println("线程"+Thread.currentThread().getName()+"回应命令处理结果");
                        //共有三个线程,每个线程执行到这里,cdAnswer就会减少一个
                        cdAnswer.countDown();
                    }catch (InterruptedException e){
                    }
                }
            };
            executorService.execute(runnable);
        }
        try {
            Thread.sleep((long) (Math.random()*10000));
            System.out.println("线程"+Thread.currentThread().getName()+"即将发布命令");
            cdOrder.countDown();
            System.out.println("线程"+Thread.currentThread().getName()+"已经发送命令,正在等待结果");
            //cdAnswer初始值是3,主线程执行到这里时会阻塞,直到上面的cdAnswer.countDown();减少为0,
            //主线程才继续执行
            cdAnswer.await();
            System.out.println("线程"+Thread.currentThread().getName()+"已经收到所有响应结果");
        }catch (Exception e){
        }
        executorService.shutdown();
    }
}
2.CyclicBarrier类
public class CyclicBarrirTest {
    public static void main(String[] args) {
        ExecutorService executorService = Executors.newCachedThreadPool();
        final CyclicBarrier cyclicBarrier = new CyclicBarrier(3);
        for (int i = 0; i < 3; i++) {
            Runnable runnable = new Runnable() {
                @Override
                public void run() {
                    try {
                        Thread.sleep((long) (Math.random()*10000));
                        System.out.println("线程"+Thread.currentThread().getName()+"即将到达集合地点" +
                                ",当前已经有 "+(cyclicBarrier.getNumberWaiting()+1)+"已经到达。"+
                                (cyclicBarrier.getNumberWaiting()==2?"都到齐了,一起走啊":"继续等待"));
                        cyclicBarrier.await();
                    }catch (InterruptedException e){
                    }catch (BrokenBarrierException e) {
                        e.printStackTrace();
                    }
                }
            };
            executorService.execute(runnable);
        }
        executorService.shutdown();
    }
}
多线程系列之十一:Two-Phase Termination模式的更多相关文章
- Java 设计模式系列(十一)享元模式
		
Java 设计模式系列(十一)享元模式 Flyweight 享元模式是对象的结构模式.享元模式以共享的方式高效地支持大量的细粒度对象. 一.享元模式的结构 享元模式采用一个共享来避免大量拥有相同内容对 ...
 - 多线程系列之九:Worker Thread模式
		
一,Worker Thread模式 也叫ThreadPool(线程池模式) 二,示例程序 情景:一个工作车间有多个工人处理请求,客户可以向车间添加请求.请求类:Request定义了请求的信息和处理该请 ...
 - Java多线程编程模式实战指南(三):Two-phase Termination模式
		
停止线程是一个目标简单而实现却不那么简单的任务.首先,Java没有提供直接的API用于停止线程.此外,停止线程时还有一些额外的细节需要考虑,如待停止的线程处于阻塞(等待锁)或者等待状态(等待其它线程) ...
 - Java多线程编程模式实战指南(三):Two-phase Termination模式--转载
		
本文由本人首次发布在infoq中文站上:http://www.infoq.com/cn/articles/java-multithreaded-programming-mode-two-phase-t ...
 - Java多线程系列--“JUC锁”03之 公平锁(一)
		
概要 本章对“公平锁”的获取锁机制进行介绍(本文的公平锁指的是互斥锁的公平锁),内容包括:基本概念ReentrantLock数据结构参考代码获取公平锁(基于JDK1.7.0_40)一. tryAcqu ...
 - Java多线程系列--“JUC锁”04之 公平锁(二)
		
概要 前面一章,我们学习了“公平锁”获取锁的详细流程:这里,我们再来看看“公平锁”释放锁的过程.内容包括:参考代码释放公平锁(基于JDK1.7.0_40) “公平锁”的获取过程请参考“Java多线程系 ...
 - Java多线程系列--“JUC锁”05之 非公平锁
		
概要 前面两章分析了"公平锁的获取和释放机制",这一章开始对“非公平锁”的获取锁/释放锁的过程进行分析.内容包括:参考代码获取非公平锁(基于JDK1.7.0_40)释放非公平锁(基 ...
 - Java多线程系列--“JUC锁”08之 共享锁和ReentrantReadWriteLock
		
概要 Java的JUC(java.util.concurrent)包中的锁包括"独占锁"和"共享锁".在“Java多线程系列--“JUC锁”02之 互斥锁Ree ...
 - Java多线程系列--“JUC线程池”02之 线程池原理(一)
		
概要 在上一章"Java多线程系列--“JUC线程池”01之 线程池架构"中,我们了解了线程池的架构.线程池的实现类是ThreadPoolExecutor类.本章,我们通过分析Th ...
 
随机推荐
- windowsserver2019系统下载
			
windowsserver2019系统分为标准版和数据中心版,两个版本和windows2012,2016一样没有64位系统,点击下载windowsserver2019系统.
 - php学习----错误处理和代码重用
			
php错误处理 一.错误分类:1.语法错误 2.运行时错误 3.逻辑错误 错误代号(部分): 所有看到的错误代码在php中都被定义为系统常量(可以直接使用) 1)系统错误 E_PARSE:编译错误,代 ...
 - 【大数据技术】操作系统和Hadoop版本选择
			
1.操作系统选择 Hadoop产品是由Java语言开发的,所以推荐的是Linux操作系统,理由很简单开源免费,推荐的操作系统CentOS. CentOS是一个基于Red Hat 企业级 Linux 提 ...
 - VsCode放大缩小
			
如图:vscode界面突然缩小了 通过快捷键 ctrl+shift+ + 放大 ctrl+shift+ - 缩小
 - MySQL高级知识(十三)——表锁
			
前言:锁是计算机协调多个进程或线程并发访问某一资源的机制.在数据库中,除传统的计算机资源(如CPU.RAM.I/O等)的争用外,数据也是一种供许多用户共享的资源.如何保证数据并发访问的一致性.有效性是 ...
 - linux学习笔记整理(八)
			
第九章 文件的归档和压缩本节所讲内容:9.1 tar命令进行文件的归档和压缩9.2 zip管理压缩文件9.3 了解gzip-bzip2- xz管理压缩文件-file-sort查看文件 9.1 tar命 ...
 - WPF中控件的显示与隐藏
			
1.WPF中控件的显示与隐藏的属性是 Visibility,它有3个枚举值 Visible, Hidden 和 Collapsed.其中Visible为可见,而 Hidden 和 Collapsed ...
 - 【window】window10永久关闭更新
			
在使用pc过程中自己遇到的问题 相关资料:http://www.ghost580.com/win10/2016-10-21/17295.html 作者:smile.轉角 QQ:493177502
 - 004_Python高级特性(1):Iterators、Generators和itertools(参考)
			
对数学家来说,Python这门语言有着很多吸引他们的地方.举几个例子:对于tuple.lists以及sets等容器的支持,使用与传统数学类 似的符号标记方式,还有列表推导式这样与数学中集合推导式和集的 ...
 - hyperledger中文文档学习-2-简介
			
参考https://hyperledgercn.github.io/hyperledgerDocs/blockchain_zh/ Hyperledger区块链框架(https://blog.csdn. ...