线程池优雅关闭

如果没有额外引用jar包,spring项目中使用线程池一般有两种方法;

ThreadPoolExecutor
   private static final ThreadPoolExecutor threadPoolExecutor = 
new ThreadPoolExecutor(2,4,0,
            TimeUnit.MINUTES,new LinkedBlockingQueue<>());

    threadPoolExecutor.execute(()->{});

这种方式下,线程池没有交给spring管理,队列及在执行中的任务会直接丢弃;

需要手动在PreDestory中进行处理;

    public void preDestroy() throws InterruptedException {
        log.info("preDestroy");
        log.info("线程池中队列数量:"+threadPoolExecutor.getQueue().size());
        threadPoolExecutor.shutdown(); // 拒绝新任务加入
        // 立即关闭线程池  返回false
//        threadPoolExecutor.shutdownNow();  // 会中断
        // 超时未完成  返回false
        if(threadPoolExecutor.awaitTermination(10L,TimeUnit.SECONDS)){
            log.info("关闭");
            log.info("线程池中线程数量:"+threadPoolExecutor.getQueue().size());
        }else{
            log.info("未安全关闭");
            log.info("线程池中线程数量:"+threadPoolExecutor.getQueue().size());
        }
    }
  • shutdown:
    不再接收新的任务,等待已提交任务执行完成, 通过以下几个步骤完成
    •  设置线程池状态为shutdown, 而非runing状态下 addWoker都是返回的false, 会进入 rejectedExecution 
    • 调用 interruptIdleWorkers 释放空闲线程 获得任务的线程会拿到锁,所以在tryLock中是失败的  这里不会中断执行中的任务
  • shutdownNow:尝试停止所有正常执行的任务,并返回等待执行的队列列表, 通过以下几个步骤完成
    • 设置状态为stop ,  同shutdown,stop状态也是拒绝新增任务,同时runWorker中新拿到的任务也是会进行中断 尝试停止任务
    • 调用interruptWorkers  对所有任务进行中断 尝试停止
  • awaitTermination: 等待线程池关闭
spring @Async方式

这类线程池继承了ExecutorConfigurationSupport  

默认调用shutdownNow 并调用remainingTask.cancal 

  • 4
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值