ThreadPoolExecutor中的keepAliveTime详解
文章目录
- 一、keepAliveTime的概念
- 二、keepAliveTime的设置方法
- 2.1. 通过构造函数设置
- 2.2. 通过setKeepAliveTime方法动态设置
- 三、线程是如何根据keepAliveTime进行销毁的
阅读这篇文章,你将会知道:
keepAliveTime的概念。
keepAliveTime是如何设置的。
线程是如何根据keepAliveTime进行销毁的。
一、keepAliveTime的概念
- 1 keepAliveTime的单位是纳秒,即1s=1000000000ns,1秒等于10亿纳秒。
- 2 keepAliveTime是线程池中空闲线程等待工作的超时时间。
- 3 当线程池中线程数量大于corePoolSize(核心线程数量)或设置了allowCoreThreadTimeOut(是否允许空闲核心线程超时)时,线程会根据- 1 keepAliveTime的值进行活性检查,一旦超时便销毁线程。
- 4 否则,线程会永远等待新的工作。
/*** Timeout in nanoseconds for idle threads waiting for work.* Threads use this timeout when there are more than corePoolSize* present or if allowCoreThreadTimeOut. Otherwise they wait* forever for new work.*/private volatile long keepAliveTime;
二、keepAliveTime的设置方法
2.1. 通过构造函数设置
通过 keepAliveTime 、unit共同决定实际的 keepAliveTime值,最终会转化成纳秒单位。
2.2. 通过setKeepAliveTime方法动态设置
重新设置线程池的keepAliveTime属性,如果发现将要设置的值比原来的keepAliveTime值要小(即减小keepAliveTime),则触发interruptIdleWorkers(),中断空闲线程。
interruptIdleWorkers()是怎么中断线程的呢?
(1)interruptIdleWorkers先拿出所有的工作者进行遍历,判断工作者对应的线程是否已经中断。
(2)如果没有产生中断,则判断是否可以获得锁,如果能获得锁,则代表是空闲线程,然后中断该线程。
(3)至于线程的中断在什么时候会抛出中断异常,同学们可以自己找下资料,也可以参考下别人写的这篇文章Java并发之线程中断
三、线程是如何根据keepAliveTime进行销毁的
1.线程池中的线程通过工作者(Worker)这个类进行包装,Worker通过 ThreadPoolExecutor.runWorker() 这个方法进行自旋,从队列中获得task,并完成工作。
2.如果拿不到task(即firstTask == null 或 getTask() == null),则会退出自旋,进入finally代码块。finally中会调用processWorkerExit方法,注销当前Worker,实现worker的销毁。对keepAliveTime的使用,就在getTask()方法中,这个在后面讲解。
3.getTask 怎么使用 keepAliveTime
(1)首先也是一个自旋,当allowCoreThreadTimeout(运行空闲核心线程超时) 或 wc>corePoolSize(当前线程数量大于核心线程数量) 时,timed会标识为true,表示需要进行超时判断。
(2)当wc(当前工作者数量)大于 最大线程数 或 空闲线程的空闲时间大于keepAliveTime(timed && timeout),以及wc>1或(workQueue)任务队列为空时,会进入compareAndDecrementWorkerCount方法,对wc的值减1。
(3)当compareAndDecrementWorkerCount方法返回true时,则getTask方法会返回null,终止getTask方法的自旋。这时候回到runWorker方法,就会进入到processWorkerExit方法,进行销毁worker。
4.compareAndDecrementWorkerCount中操作的是ctl属性:
(1)ctl是中心控制器,一个AtomicInteger类型的整数,通过数字的二进制编码的位进行分段,不同的二进制位段表示有不同的含义。
(2)在ctl中,低29为表示线程池的容量,即线程池最大容量为 536870911 = 000 11111111111111111111111111111。
/*** The main pool control state, ctl, is an atomic integer packing* two conceptual fields* workerCount, indicating the effective number of threads* runState, indicating whether running, shutting down etc*/private final AtomicInteger ctl = new AtomicInteger(ctlOf(RUNNING, 0));// COUNT_BITS = 29private static final int COUNT_BITS = Integer.SIZE - 3;// CAPACITY = 536870911 = 000 11111111111111111111111111111private static final int CAPACITY = (1 << COUNT_BITS) - 1;private static int workerCountOf(int c) { return c & CAPACITY; }
ThreadPoolExecutor中的keepAliveTime详解相关推荐
- ALSA声卡驱动中的DAPM详解之四:在驱动程序中初始化并注册widget和route
前几篇文章我们从dapm的数据结构入手,了解了代表音频控件的widget,代表连接路径的route以及用于连接两个widget的path.之前都是一些概念的讲解以及对数据结构中各个字段的说明,从本章开 ...
- Asp.net中GridView使用详解(引)【转】
Asp.net中GridView使用详解(引) GridView无代码分页排序 GridView选中,编辑,取消,删除 GridView正反双向排序 GridView和下拉菜单DropDownList ...
- Linux中iptraf命令详解(IP局域网监控工具)
2019独角兽企业重金招聘Python工程师标准>>> Linux中iptraf命令详解(IP局域网监控工具) 发布时间:2017-12-27 20:46:03 作者:佚名 ...
- ArcGIS Engine中的Symbols详解
转自原文 ArcGIS Engine中的Symbols详解 本文由本人翻译ESRI官方帮助文档.尊重劳动成果,转载请注明来源. Symbols ArcObjects用了三种类型的Symbol(符号样式 ...
- js路由在php上面使用,React中路由使用详解
这次给大家带来React中路由使用详解,React中路由使用的注意事项有哪些,下面就是实战案例,一起来看一下. 路由 通过 URL 映射到对应的功能实现,React 的路由使用要先引入 react-r ...
- Linux中etc目录详解
Linux中etc目录详解 /etc目录 包含很多文件.许多网络配置文件也在/etc 中. /etc/rc or/etc/rc.d or/etc/rc*.d 启动.或改变运行级时运行的sc ...
- java 自定义正则表达式_java中正则表达式实例详解
Java中正则表达式运用实例(参看java中正则表达式运用详解): 测试代码 package test; /** * 在String的matches()方法,split()方法中使用正则表达式. * ...
- numpy中reshape方法详解
numpy中reshape方法详解_zhanggonglalala的博客-CSDN博客_reshape
- JavaScript中getBoundingClientRect()方法详解
JavaScript中getBoundingClientRect()方法详解 getBoundingClientRect() 这个方法返回一个矩形对象,包含四个属性:left.top.right和bo ...
最新文章
- LeetCode Remove Duplicates from Sorted List II
- redis3.2.3安装部署实战
- 如何跟随有三从零进阶中级CV算法工程师
- python中dict的fromkeys用法教程
- 免费2款标注工具实操(内含下载链接)
- Android 用java代码动态修改UI界面
- You Probably Dont Need Derived State
- atitit.404错误的排查流程总结vOa6
- 【亲测有效】解决电脑不能复制粘贴的几种方法
- oceancolor数据批量下载
- 互联网变迁-真实化信息的转移
- Django的模板语言DTL介绍以及渲染方式
- ModuleNotFoundError: No module named ‘myitem.myapp‘
- TIA博途中如何使用符号方式按位,字节,字访问非结构数据类型
- 周报 | 吉吉拍数字商品交易平台
- 2021年四川省大学生信息安全技术大赛部分WP (四川省赛WP)
- Linux雷鸟邮件,thunderbird雷鸟mail
- DAU ARPU 美术
- 韶关学院计算机科学学院简介
- 如何在win11上浏览政府IE网站
热门文章
- “骗子”成民企院士第一人:把认真当信仰,人生就会开挂
- 任正非:感谢美国,帮我把华为给全世界都宣传了
- 赌场圣手(从不失手)——隐马尔可夫!
- linux双屏播放视频,Ubuntu Linux下双屏显示解决方案
- 获取网站服务器数据库,利用XmlHttp获取服务器数据库数据以表格的方式返回客户的代码示例...
- java邮箱exchange_使用Javamail访问Microsoft Exchange邮箱(IMAP,MS Exchange)
- Python 的协程
- 优先队列c++ STL用法
- Windows 中_T和L
- 海云健康:上云为10万家药店带去了什么价值?