线程池原理分析

介绍一篇总结的很好的博客:https://blog.csdn.net/qq_25806863/article/details/71126867

一、概述

线程池:是创建多个线程并且进行管理的容器。(线程池是个容器,可以创建线程和管理线程,并且给线程分配任务)。

在Java中创建一个线程其实是一个很简单的事情,只要new Thread就可以了,但是这样做并不是一种很好的方式:

比如在一个项目里,全部都是用的new Thread的方式去启用线程,那么创建好Thread1,而1在运行的时候,创建了Thread2,等等等... 创建了10个线程的时候,1,2,3都执行完毕了但是没被销毁,就可能导致无限制的新建线程,相互竞争,占用过多的系统资源,导致死锁以及OOM。

而且这些线程缺乏统一的管理的功能,也缺乏定期执行,定时执行,线程中断的功能。

二、使用线程池的好处

(1) 重用已经存在的线程,减少了线程的创建和销毁的开销。

(2)可有效控制最大并发的线程数,提高了系统资源的使用率避免很多竞争,避免了OOM啊 死锁啊等。

(3)可以提供定时和定期的执行方式,单线程,并发数量的控制等功能!

三、五种类型线程池

  • newSingleThreadExecutor一个单线程的线程池,可以用于需要保证顺序执行的场景,并且只有一个线程在执行。
  • newFixedThreadPool一个固定大小的线程池,可以用于已知并发压力的情况下,对线程数做限制。
  • newCachedThreadPool一个可以无限扩大的线程池,比较适合处理执行时间比较小的任务。
  • newScheduledThreadPool可以延时启动,定时启动的线程池,适用于需要多个后台线程执行周期任务的场景。
  • newWorkStealingPool一个拥有多个任务队列的线程池,可以减少连接数,创建当前可用cpu数量的线程来并行执行。

在《阿里巴巴java开发手册》中指出了线程资源必须通过线程池提供,不允许在应用中自行显示的创建线程,这样一方面是线程的创建更加规范,可以合理控制开辟线程的数量;另一方面线程的细节管理交给线程池处理,优化了资源的开销

而线程池不允许使用Executors去创建,而要通过ThreadPoolExecutor方式,这一方面是由于jdk中Executor框架虽然提供了如newFixedThreadPool()、newSingleThreadExecutor()、newCachedThreadPool()等创建线程池的方法,但都有其局限性,不够灵活;另外由于前面几种方法内部也是通过ThreadPoolExecutor方式实现,使用ThreadPoolExecutor有助于大家明确线程池的运行规则,创建符合自己的业务场景需要的线程池,避免资源耗尽的风险

四、创建线程池

一、可以使用工具类Executors的静态方法来获取线程池或静态方法:

  • ExecutorService service1 = Executors.newSingleThreadExecutor();
  • ExecutorService service2 = Executors.newCacheThreadPool();
  • ExecutorService service3 = Executors.newFixedThreadPool(10);
  • ExecutorService service4 = Executors.newScheduledThreadPool(10);

二、可以使用过工具类ThreadPoolExecutor,通过构造方法的一系列参数,来构成不同配置的线程池。常用的构造方法有下面四个:

ThreadPoolExecutor(int corePoolSize,
                        int maximumPoolSize,
                        long keepAliveTime,
                        TimeUnit unit,
                        BlockingQueue<Runnable> workQueue) 

ThreadPoolExecutor(int corePoolSize,
                        int maximumPoolSize,
                        long keepAliveTime,
                        TimeUnit unit,
                        BlockingQueue<Runnable> workQueue,
                        ThreadFactory threadFactory)

ThreadPoolExecutor(int corePoolSize,
                        int maximumPoolSize,
                        long keepAliveTime,
                        TimeUnit unit,
                        BlockingQueue<Runnable> workQueue,
                        RejectedExecutionHandler handler)

ThreadPoolExecutor(int corePoolSize,
                        int maximumPoolSize,
                        long keepAliveTime,
                        TimeUnit unit,
                        BlockingQueue<Runnable> workQueue,
                        ThreadFactory threadFactory,
                        RejectedExecutionHandler handler)
  • corePoolSize

核心线程数,默认情况下核心线程会一直存活,即使处于闲置状态也不会受存keepAliveTime限制。除非将allowCoreThreadTimeOut设置为true。

  • maximumPoolSize

线程池所能容纳的最大线程数。超过这个数的线程将被阻塞。当任务队列为没有设置大小的LinkedBlockingDeque时,这个值无效。

  • keepAliveTime

非核心线程的闲置超时时间,超过这个时间就会被回收。

  • unit

指定keepAliveTime的单位,如TimeUnit.SECONDS。当将allowCoreThreadTimeOut设置为true时对corePoolSize生效。

  • workQueue

线程池中的任务队列.

常用的有三种队列,SynchronousQueue,LinkedBlockingDeque,ArrayBlockingQueue。

  • threadFactory

线程工厂,提供创建新线程的功能。ThreadFactory是一个接口,只有一个方法
 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值