package com.study.test.all.threadpool; import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.ThreadPoolExecutor; import java.util.concurrent.TimeUnit; public class UsingThreadPool { public static void main(String[] args){ ThreadPoolExecutor executor = new ThreadPoolExecutor(5,10,200, TimeUnit.MILLISECONDS,new ArrayBlockingQueue<Runnable>(5)); for(int i=0; i<15; i++){ MyTask myTask = new MyTask(i); executor.execute(myTask); System.out.println("线程池中线程的数目:"+executor.getPoolSize()+",队列中等待执行的任务数目:"+ executor.getQueue().size()+",已执行玩完的任务数目:"+executor.getCompletedTaskCount()); } executor.shutdown();//关闭线程池 } }
public class MyTask implements Runnable { private int taskNum;//任务的编号 public MyTask(int taskNum) { this.taskNum = taskNum; } @Override public void run() { System.out.println("正在执行task"+taskNum); try { Thread.sleep(4000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("task"+taskNum+"执行完毕!"); } }
执行结果:
正在执行task0 线程池中线程的数目:1,队列中等待执行的任务数目:0,已执行玩完的任务数目:0 线程池中线程的数目:2,队列中等待执行的任务数目:0,已执行玩完的任务数目:0 线程池中线程的数目:3,队列中等待执行的任务数目:0,已执行玩完的任务数目:0 正在执行task1 线程池中线程的数目:4,队列中等待执行的任务数目:0,已执行玩完的任务数目:0 线程池中线程的数目:5,队列中等待执行的任务数目:0,已执行玩完的任务数目:0 正在执行task2 线程池中线程的数目:5,队列中等待执行的任务数目:1,已执行玩完的任务数目:0 线程池中线程的数目:5,队列中等待执行的任务数目:2,已执行玩完的任务数目:0 线程池中线程的数目:5,队列中等待执行的任务数目:3,已执行玩完的任务数目:0 正在执行task3 线程池中线程的数目:5,队列中等待执行的任务数目:4,已执行玩完的任务数目:0 线程池中线程的数目:5,队列中等待执行的任务数目:5,已执行玩完的任务数目:0 正在执行task4 线程池中线程的数目:6,队列中等待执行的任务数目:5,已执行玩完的任务数目:0 线程池中线程的数目:7,队列中等待执行的任务数目:5,已执行玩完的任务数目:0 正在执行task10 线程池中线程的数目:8,队列中等待执行的任务数目:5,已执行玩完的任务数目:0 线程池中线程的数目:9,队列中等待执行的任务数目:5,已执行玩完的任务数目:0 线程池中线程的数目:10,队列中等待执行的任务数目:5,已执行玩完的任务数目:0 正在执行task11 正在执行task12 正在执行task13 正在执行task14 task2执行完毕! task0执行完毕! task1执行完毕! 正在执行task7 task10执行完毕! task3执行完毕! 正在执行task8 task4执行完毕! 正在执行task9 正在执行task6 正在执行task5 task14执行完毕! task11执行完毕! task13执行完毕! task12执行完毕! task7执行完毕! task5执行完毕! task9执行完毕! task6执行完毕! task8执行完毕!
从执行结果可以看出,当线程池中线程的数目大于5时,便将任务放入任务缓存队列里面,当任务缓存队列满了之后,便创建新的线程。
如果上面程序中,将for循环中改成执行20个任务,就会抛出任务拒绝异常了。
不过在java doc中,并不提倡我们直接使用ThreadPoolExecutor,而是使用Executors类中提供的几个静态方法来创建线程池:
Executors.newCachedThreadPool(); //创建一个缓冲池,缓冲池容量大小为Integer.MAX_VALUE
Executors.newSingleThreadExecutor(); //创建容量为1的缓冲池
Executors.newFixedThreadPool(int); //创建固定容量大小的缓冲池
参考: