Java线程池

本文介绍了数据库连接池与Java线程池的概念,它们如何通过复用连接/线程减少创建/销毁开销,以及线程池的主要优点如提高性能、控制并发和资源管理。还讨论了线程池的应用场景和JDK提供的ThreadPoolExecutor实现。
摘要由CSDN通过智能技术生成

数据库连接池的概念

我们之前学习过的数据库连接池,在某种程度上和Java线程池是思路一致的。

因为频繁的创建数据库的连接对象,又销毁,在时间上开销较大。所以使用集合存储一些 事先创建出的连接对象,每次使用时,从集合中获取,用完不销毁,减少频繁创建,又销毁;

数据库连接池、线程池 意思都是类似的;

线程池是什么?

它是一种并发编程的技术,用于管理并发执行的线程。他预先创建一组线程,并维护一个任务队列,用于存储需要执行的任务。当有任务到达时,线程池从队列中获取一个空闲的线程来执行任务,当任务执行完毕后,线程将返回线程池中,等待下一个任务。

线程池的主要优点是提高了线程的复用性和性能。通过预先创建一组线程,并且避免了线程的创建和销毁开销,可以减少系统的开销,提高任务的执行效率。线程池可以控制同时执行的线程数量,避免系统资源被过度消耗,可以有效地管理系统的并发度。

线程池通常用于多线程的场景,例如服务器端的请求处理、并发任务处理等。它可以使程序更稳定、可伸缩,并且能够提供更好的性能和资源管理。

为什么会有线程池?

  1. 减少线程创建和销毁的开销:创建和销毁线程是一个比较消耗资源的操作,频繁地创建和销毁线程会增加系统开销。而线程池通过事先创建一组线程,并将其保存在池中,可以避免频繁地创建和销毁线程,提高系统性能和资源利用率。

  2. 控制并发度:线程池可以限制线程的数量,通过设置线程池的大小,可以控制同时执行的线程数。这样可以避免线程数量过多导致系统资源耗尽,避免过度竞争和阻塞,提高系统的稳定性和吞吐量。

  3. 提高任务处理效率:线程池能够将任务进行排队,当有任务到达时,线程池会从队列中获取一个可用的线程来执行任务。通过任务队列,线程池可以有效地管理任务的执行顺序和调度,避免任务之间的冲突和竞争,并且可以提高任务的执行效率。

  4. 提供线程管理和监控机制:线程池可以提供对线程的管理和监控机制,例如可以统计线程的执行情况、线程的状态和健康状况等信息。这些信息可以用于系统性能优化、故障排查和监控报警等目的。

综上所述,引入线程池可以提高系统的性能和稳定性,优化资源利用,提高任务处理效率,同时提供线程管理和监控机制,更方便地管理和调优系统。因此,线程池在多线程编程中得到了广泛的应用。

 

线程池是什么结构?

实质是集合,存储的线程

首先,线程池并不是像堆、栈那样的存储空间。线程池是一种并发编程的技术,用于管理并发执行的线程。它实际上是一个线程的集合,其中包含了多个预先创建的线程。

线程池内部通常维护一个任务队列,用于存储需要执行的任务。当有任务到达时,线程池会从队列中获取一个空闲的线程来执行该任务。任务执行完毕后,线程将返回线程池中等待下一个任务。

线程池的主要目的是提高线程的复用性和性能,减少线程的创建和销毁开销,并且控制并发度,以提高系统的稳定性和资源利用率。虽然线程池可能需要一定的存储空间来存储线程池对象、任务队列等数据结构,但线程池本身并不是用来存储数据的存储空间。

线程池主要用于什么地方?

线程池主要用于在多线程编程中管理和调度线程,提高并发任务的执行效率和系统的性能。以下是一些常见的应用场景:

  1. 服务器端编程:在服务器端应用程序中,通常需要同时处理多个客户端请求。使用线程池可以控制并发度,避免过多的线程同时处理请求,从而提高服务器的吞吐量和响应速度。

  2. Web应用程序中的请求处理:在Web开发中,服务器需要同时处理多个客户端请求。使用线程池可以解决并发请求的处理问题,并提供更好的性能和资源管理。

  3. 计算密集型任务:在需要进行大量计算的任务中,可以将任务分解为多个子任务,然后使用线程池并行地执行这些子任务,以提高计算效率。

  4. I/O密集型任务:在进行大量I/O操作,例如读写文件、网络通信等任务时,使用线程池可以实现异步操作,提高系统的吞吐量和响应性能。

  5. 并发数据处理:在并发数据处理场景中,例如数据抓取、数据清洗、数据分析等,可以使用线程池处理并行的数据处理任务,提高处理效率和吞吐量。

总之,任何需要并发执行任务的场景都有可能使用到线程池。线程池能够控制线程的数量、调度任务的执行,并提供线程管理和监控机制,以满足不同应用场景的需求。

具体例子:

  1. Web服务器:Web服务器需要同时处理多个客户端的请求。使用线程池可以管理并发请求的处理,避免创建过多的线程导致资源耗尽,提高服务器的性能和稳定性。

  2. 数据库连接池:在数据库访问场景中,连接数据库是一个开销较大的操作。使用线程池可以预先创建一组数据库连接,并将其保存在连接池中。当有请求到达时,线程池提供可复用的数据库连接,避免了频繁的数据库连接和断开操作,提高数据库访问的效率。

线程池

jdk5之后java增加了线程池的实现,使用ThreadPoolExecutor类实现线程池创建和管理.

池的好处

减少频繁创建销毁时间,统一管理线程,提高速度。

ThreadPoolExecutor类图

 

通常使用ThreadPoolExecutor

1.线程池状态

使用ctl变量存储线程池的状态

ThreadPoolExecutor使用int的高3位来表示线程池状态,低29位表示线程数量

 

为什么要将线程池状态和线程数量存在一个变量中?

这些信息存储在一个原子变量ctl中,目的是将线程池状态与线程个数合二为一,这样就可以用一次cas原子操作进行赋值。

2.ThreadPoolExcutor构造方法

  • corePoolSize核心线程数目(最多保留的线程数)

  • maximumPoolSize最大线程数目

  • keepAliveTime生存时间-针对救急线程

  • unit时间单位-针对救急线程

  • workQueue阻塞队列;他也有大小

  • threadFactory线程工厂-可以为线程创建时起个好名字;可以把线程池中的线程和其他线程区分开来

  • handler拒绝策略

工作方式

c为核心线程数,m为最大线程数(核心+救急)

核心线程数就是线程池一次可以执行的线程数目,而如果线程池已经达到核心线程数了,还有任务过来,那么这线程就会进入阻塞队列中,如果阻塞队列也满了,还有任务过来,那么就需要救急线程出动了,救急线程执行完任务后,就会销毁,结束,下次高峰期来了,再重新创建(核心线程运行完任务了,还会保留在线程池);在此期间,线程池中所有线程都已经有任务,救急线程都已经满员时,此时若再来任务,才进行拒绝策略。

具体一点:

 

 

 

3.newFixedThreadPool

fixed固定的意思,即固定线程数的线程池,指的是核心线程数固定,而阻塞队列的数量是无限的。

 

 

特点:

  • 核心线程数==最大线程数(没有救急线程被创建)因此也无需超时时间

  • 阻塞队列是无界的,可以放任意数量的任务

评价:适用于任务量已知,相对耗时的任务。

4.newCachedThreadPool

带缓冲功能的线程池

  

特点

  • 核心线程数为0,最大线程数是Integer.MAX_VALUE,救急线程的空闲生存时间是60s,意味着

    • 全部都是救急线程(60s后可以回收)

    • 救急线程可以无限创建

  • 队列采用了SynchronizedQueue实现,特点是,它没有容量,没有线程来取是放不进去的(一手交钱,一手交货)

评价:整个线程池表现为线程数会根据任务量不断增长,没有上限,当任务执行完毕,空闲一分钟后释放线程。

适合任务数比较密集,但每个任务执行时间较短的情况

5.newSingleThreadExcutor

单线程执行器,线程池中只有一个使用场景核心线程,没有救急线程,可以从下面的参数看出

 

 

使用场景:

希望多个任务排队执行。线程数固定为1,任务数多于1时,会放入无界队列排队。任务执行完毕,这唯一的线程也不会被释放。

自己创建一个线程和用单线程池的区别?

  • 自己创建一个单线程串行执行任务,如果任务执行失败而终止那么没有任何补救措施,而线程池还会新建一个线程,保证池的正常工作

  • Executors.newSingleThreadExecutor()线程个数始终为1.不能改变

  • FinalizableDelegatedExecutorService应用的是装饰器模式,只对外暴露了ExecutorService接口,因此不能调用ThreadPoolExecutor中特有的方法

  • Executors.newFixedThreadPool(1)初始时为1,以后还可以修改

    • 对外暴露的是ThreadPoolExecutor对象,可以强转后调用setCorePoolSize等方法进行修改

6.线程池提交任务

参数是runnable接口,相当于传进来一个线程要执行的内容

 

7.关闭线程池
shutdown()方法

线程池状态变为SHUTDOWN

  • 不会接收新任务

  • 但已提交任务会执行完

  • 此方法不会阻塞调用线程的执行

 

shutdownNow()方法

线程池状态变为STOP

List<Runnable> shutdownNow();

  • 不会接收新任务

  • 会将队列中的任务返回

  • 并用interrupt的方式中断正在执行的任务

 

其他方法

 

 

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值