java线程池灵魂8个问题

avatar
作者
筋斗云
阅读量:0

一、线程池的基础总结

1、线程池的状态机器以及对应的状态流转

2、线程池如何表示状态以及线程数

3、线程池的核心参数

4、线程池的执行过程

5/1如何实现非核心线程延迟死亡?

非核心线程延迟死亡条件为:线程池处于运行状态&&当前线程数大于最大核心线程数&&获取任务超时时间keepAliveTime

5/2 如何实现核心线程一直保活?

通过阻塞队列的take()方法让线程一直等待,使得Worker的run()方法一直阻塞,直到获取到执行的任务,执行完毕任务后继续阻塞等待,使得线程生命周期一直在RUNNABLE和WAITING状态之间流转,保证核心线程一直存活

5/3 如何释放核心线程?

allowCoreThreadTimeOut这个成员变量,将这个变量设置为true就可以跟非核心线程一样,在执行keepAliveTime还未获取到执行任务时候就移出线程池

5/4非核心线程能成为核心线程吗?

创建Worker线程类并没有识别出表示一个线程是核心线程还是非核心线程

5/5线程池如何保证并发安全?

1、线程池状态和工作线程数量的并发

2、Worker容器变更的并发(添加或者删除线程)

问题1 使用AtomicInteger使用cas+volitile保证锁

微博图2对于worker集合采用的是ReetrantLock锁保证,同一个时间只有一个线程可以操作集合对象,

问题3,并发安全工作由队列BlockingQueue本身保证线程安全,内部实现使用ReetranLock实现,

5/6 线程数设置多少是合理的

5/7存放线程对象的容器为什么使用HashSet?

工作线程类Worker恶灵实现Runnable接口,他是对线程池中工作线程的抽象,ThreadsPoolexecutor对worker集合HashSet只有add和remove才做,HashSet是基于HashMap来实现的,只要Hash函数和负载因子设计的足够好,操作HashSet效率就会足够的高O(1)

5/8 结合源码介绍下线程池设计思路?

1任务处理策略:线程池优先使用核心线程来处理任务,从任务添加策略可以看出,先考虑创建核心线程处理,在考虑放到阻塞队列,然后考虑创建非核心线程,达到饱和之后使用拒绝策略

2、线程生命周期管理:通过向阻塞队列取任务的不同操作,确保线程的存活,take()保证核心线程不死,poll保证非和核心线程等待一定时间后释放

3、容量管理:线程池不区分核心线程和非核心线程,线程池期望达到corepoolSize的并发状态,并允许在不得已情况下超载,达到orepoolsize~manmumPoolSize并发状态

4、状态管理:线程池状态和数量使用ctl表示,高3位,低29位表示线程池数量。线程池对状态检查非常苛刻,几乎在所有稍微好事或者影响下一步操作正确性代码都校验ctl

广告一刻

为您即时展示最新活动产品广告消息,让您随时掌握产品活动新动态!