本文共 1481 字,大约阅读时间需要 4 分钟。
ThreadPoolExcutor中有四个内部类实现了线程池的拒绝策略。当然我们也可以自己定义,这里讲解一下这四个已经实现的拒绝策略。
在什么情况下,线程池会拒绝新提交的任务呢。
在ThreadPoolExcutor的构造方法中,有这几个参数,参数的意义请参考: 当maximumPoolSize和workQueue达到最大时,线程池会拒绝新的任务的提交public class ThreadPoolDemo { public static void main(String[] args) { ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(1,1,20, TimeUnit.MINUTES, new ArrayBlockingQueue<>(1),new ThreadPoolExecutor.AbortPolicy()); for (int i = 0; i < 3; i++) { final int temp = i; threadPoolExecutor.execute(new Runnable() { @Override public void run() { try { Thread.sleep(4000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(Thread.currentThread().getName() + "完成" + temp); } }); } }}
这里我们创建了线程池的核心线程数只有1,最大线程数也只有1,工作队列也只有1,下面我们提交了三个任务。当第一个任务提交时,此时会创建一个新的线程,当第二个任务提交时,此时因为线程池中的线程数==核心线程数,且工作队列未满,任务2加入工作队列。当第三个任务到达时,因为线程池中的线程数等于核心线程数,且工作队列以及满了,同时,线程池中的最大线程数也已经到达了,所以任务3将被拒绝。
这里我们先演示AbortPolicy。这个拒绝策略当新的任务被拒绝时,会跑出一个异常
运行结果如下: 这里我们看到,新提交的任务没有运行,并且抛出了一个异常这个拒绝策略将会悄悄的忽略掉被拒绝的任务,也不会抛出异常
运行结果: 既没有抛出异常,也没有运行任务这个拒绝策略将执行该任务,但是有提交者自己执行
运行结果: 这里虽然执行了任务2,但是该任务所执行的线程是在main(即它的提交者)这个拒绝策略将会把最先进入工作队列的任务出队,为新的任务腾出位置
运行结果: 这里可以看到,最先进入工作队列的任务1被出队了。转载地址:http://idtzi.baihongyu.com/