创建几种线程池的简单介绍

1.newFixedThreadPool,该线程池使用的是一个无界队列,即会往队列中不断增加任务,如果新增任务的速度大于处理任务的速度,那么有可能会造成内存耗尽.

  //创建方式 
  ExecutorService executorFixed = Executors.newFixedThreadPool(5);

//查看源码
在这里插入图片描述
从源码得知,该线程池用的LinkedBlockingQueue阻塞队列,该阻塞队列如果没有设置数量,默认为Integer.MAX_VALUE 核心线程数和最大线程数是一样的.


2.newSingleThreadExecutor,从名字可以得知该线程池为单线程线程池.

	//创建方式
   ExecutorService executorSingle = Executors.newSingleThreadExecutor();

查看源码:
在这里插入图片描述
从源码得知,发现核心线程数和最大线程数都为1.

代码示例是否是单线程执行:

  Runnable runnable = new Runnable() {
            @Override
            public void run() {
                try {
                    Thread.sleep(1000);
                    System.out.println(Thread.currentThread().getName() + System.currentTimeMillis());
                } catch (Exception e) {
                }
            }
        };

        for (int i = 0; i < 5; i++) {
            Thread thread = new Thread(runnable, ("Thread-" + i));
            executorSingle.execute(thread);
        }

测试结果:
在这里插入图片描述


3.newCachedThreadPool,这个线程池使用的是SynchronousQueue同步队列,即队列中不存储任务,一旦有新的任务,会不断创建线程去执行任务. 当线程池中没有线程时,该线程池会自动关闭.

//创建方式
 ExecutorService executorCache = Executors.newCachedThreadPool();

查看源码:
在这里插入图片描述
发现核心线程数为0,最大线程数为Integer.MAX_VALUE,使用的是SynchronousQueue队列.

代码示例该线程池会自动关闭:

  Runnable runnable = new Runnable() {
            @Override
            public void run() {
                try {
                    Thread.sleep(1000);
                    System.out.println(Thread.currentThread().getName() + System.currentTimeMillis());
                } catch (Exception e) {
                }
            }
        };

        for (int i = 0; i < 5; i++) {
            Thread thread = new Thread(runnable, ("Thread-" + i));
            executorCache.execute(thread);
        }

测试结果:
在这里插入图片描述
在等待60秒之后,该线程池会自动关闭,由此得知如果核心线程数设置为0,当线程活跃时间到后,线程池会自动关闭.


4.自定义线程池.即线程池中的所有参数都自己设置.

  // 核心线程数
    protected static int CORE_THREAD_POOL = 10;

    //最大线程数
    private static int MAX_THREAD_POOL = 20;

    //线程存活时间
    private static long live = 10;

    //存放任务的阻塞队列
     private static ArrayBlockingQueue<Runnable> queue = new 				   	    							      ArrayBlockingQueue<Runnable>(10);

  //任务已满,并且线程数已经为最大线程数,此时还有新增任务,会执行对应的策略,该策略为抛出异常
    private static ThreadPoolExecutor.AbortPolicy abortPolicy = new ThreadPoolExecutor.AbortPolicy();
    
  /**
         * 自定义线程,参数全部是自己设置的.
         */
        ThreadPoolExecutor poolExecutor = new ThreadPoolExecutor(CORE_THREAD_POOL, MAX_THREAD_POOL, live,
            TimeUnit.SECONDS, queue, abortPolicy);

测试拒绝策略报异常:
将核心线程设置为1,最大线程设置为2,阻塞队列容量设置为1

 Runnable runnable = new Runnable() {
            @Override
            public void run() {
                try {
                    Thread.sleep(1000);
                } catch (Exception e) {
                }
            }
        };
        for (int i = 0; i < 5; i++) {
            Thread thread = new Thread(runnable, ("Thread-" + i));
            poolExecutor.execute(thread);
        }

结果:
在这里插入图片描述
拒绝策略的方式有好几种,详细可自己去了解.


5.线程池是如何调度的?

1.当调用线程池执行任务时,会创建线程,当创建的线程大于核心线程数时.会将任务存放到阻塞队列中.线程执行完当前任务后,会继续从阻塞队列中获取任务执行.
2. 如果阻塞队列的容量满了,线程池会重新创建线程去执行队列里的任务.线程池创建的最大线程数不超过定义的最大线程数.
3. 如果阻塞队列的容量满了,并且线程池池中的线程等于最大线程数,这时还有新增任务,这个时候线程池会调用定义的拒绝策略.


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值