线程池杂记

学自:

面试必备:Java线程池解析

一、流程:

创建一个任务时,先判断线程池中已有的线程数是否已经超过核心线程数,如果没有,则创建任务;

        如果超过核心线程数,去阻塞队列中,看阻塞队列是否已满,如果没满,则放入阻塞队列中;

        如果阻塞队列已满,则判断当前线程数是否超过最大线程数,如果没超过,则创建一个新的线程;

        如果超过最大线程数,则走异常处理流程(直接抛异常;不处理,丢弃;将阻塞队列中最早的任务丢弃,然后将其放入阻塞队列)

二、异常处理方法:

(一)线程池提交时submit:

1、try catch

2、用Future作为submit的结果,用future.get()方法,接收抛出的异常(future.get()方法要加try catch

(二)线程中处理异常:

        在工作线程的.setUnCaughtExceptionHandler(中处理未捕获到的异常

           Thread t = new Thread(r);            t.setUncaughtExceptionHandler(                    (t1, e) -> {                        System.out.println(t1.getName() + "线程抛出的异常"+e);                    });            return t;           });

(三)重写ThreadExecutorPool的afterExecute方法 处理传递的异常引用

三、线程池:

先码住:

Java 四种线程池newCachedThreadPool,newFixedThreadPool,newScheduledThreadPool,newSingleThreadExecutor - 星辰之力 - 博客园

newFixedTreadPool固定线程数线程池

  • 核心线程数和最大线程数大小一样

  • 没有所谓的非空闲时间,即keepAliveTime为0

  • 阻塞队列为无界队列LinkedBlockingQueue

newCachedTreadPool(可缓存线程的线程池)

  • 核心线程数为0

  • 最大线程数为Integer.MAX_VALUE

  • 阻塞队列是SynchronousQueue

  • 非核心线程空闲存活时间为60秒

  • 提交任务

  • 因为没有核心线程,所以任务直接加到SynchronousQueue队列。

  • 判断是否有空闲线程,如果有,就去取出任务执行。

  • 如果没有空闲线程,就新建一个线程执行。

  • 执行完任务的线程,还可以存活60秒,如果在这期间,接到任务,可以继续活下去;否则,被销毁

newSingleTreadExecutor单线程线程池

  • 核心线程数为1

  • 最大线程数也为1

  • 阻塞队列是LinkedBlockingQueue

  • keepAliveTime为0

newScheduledThreadPool(定时及周期执行的线程池)

  • 最大线程数为Integer.MAX_VALUE

  • 阻塞队列是DelayedWorkQueue

  • keepAliveTime为0

  • scheduleAtFixedRate() :按某种速率周期执行

  • scheduleWithFixedDelay():在某个延迟后执行

工作机制

  • 添加一个任务

  • 线程池中的线程从 DelayQueue 中取任务

  • 线程从 DelayQueue 中获取 time 大于等于当前时间的task

  • 执行完后修改这个 task 的 time 为下次被执行的时间

  • 这个 task 放回DelayQueue队列中

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值