【Java】线程池配置
先看JUC包自带的一个资源 线程池执行器:
初始化参数如下
ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(
corePoolSize, // 核心线程数量
maximumPoolSize, // 峰值线程数量
keepAliveTime, // 保留时限,当线程数量超出峰值数量时,保留多久后释放多余的线程资源
timeUnit, // 时限单位
synchronousQueue, // 工作队列,存放需要提交给执行器执行的任务
threadFactory, // 线程工厂
callerRunsPolicy // 任务拒绝执行处理器(拒绝策略)
);
基础参数配置:
峰值上限,保留时限,根据实际业务情况来设置
/**
* 线程数量参数 计算公式参考
* https://www.cnblogs.com/warehouse/p/10810338.html
*/
int cpuCount = Runtime.getRuntime().availableProcessors(); int corePoolSize = 2 * cpuCount; // 核心线程数量(初始化和空闲存留时的线程数量)
int maximumPoolSize = 100; // 最大线程数量 线程占用峰值上限数量
long keepAliveTime = 100; // 保留时长(当前线程数量大于核心数量时保留多久后释放多余线程)
TimeUnit timeUnit = TimeUnit.SECONDS; // 保留时长单位
几种工作队列:
/**
* SynchronousQueue队列
* SynchronousQueue是一个特殊的BlockingQueue
* 它没有容量,每执行一个插入操作就会阻塞,需要再执行一个删除操作才会被唤醒
* 反之每一个删除操作也都要等待对应的插入操作。
*/
SynchronousQueue<Runnable> synchronousQueue = new SynchronousQueue<>(); /**
* ArrayBlockingQueue有界任务队列,若有新的任务需要执行时,线程池会创建新的线程,
* 直到创建的线程数量达到corePoolSize时,则会将新的任务加入到等待队列中。
* 若等待队列已满,即超过ArrayBlockingQueue初始化的容量,则继续创建线程,直到线程数量达到maximumPoolSize设置的最大线程数量,
* 若大于maximumPoolSize,则执行拒绝策略。在这种情况下,线程数量的上限与有界任务队列的状态有直接关系,
* 如果有界队列初始容量较大或者没有达到超负荷的状态,线程数将一直维持在corePoolSize以下,
* 反之当任务队列已满时,则会以maximumPoolSize为最大线程数上限。
*/
ArrayBlockingQueue<Runnable> arrayBlockingQueue = new ArrayBlockingQueue<>(10); /**
* 无界任务队列,线程池的任务队列可以无限制的添加新的任务,
* 而线程池创建的最大线程数量就是你corePoolSize设置的数量,
* 也就是说在这种情况下maximumPoolSize这个参数是无效的,
* 哪怕你的任务队列中缓存了很多未执行的任务,当线程池的线程数达到corePoolSize后,就不会再增加了;\
* 若后续有新的任务加入,则直接进入队列等待,
* 当使用这种任务队列模式时,一定要注意你任务提交与处理之间的协调与控制,
* 不然会出现队列中的任务由于无法及时处理导致一直增长,直到最后资源耗尽的问题。
*/
LinkedBlockingQueue<Runnable> linkedBlockingQueue = new LinkedBlockingQueue<>(); /**
* PriorityBlockingQueue它其实是一个特殊的无界队列,它其中无论添加了多少个任务,线程池创建的线程数也不会超过corePoolSize的数量
* ,只不过其他队列一般是按照先进先出的规则处理任务,而PriorityBlockingQueue队列可以自定义规则根据任务的优先级顺序先后执行。
*/
PriorityBlockingQueue<Runnable> priorityBlockingQueue = new PriorityBlockingQueue<>();
线程工厂使用默认工厂提供:
/**
* ThreadFactory
*/
ThreadFactory threadFactory = Executors.defaultThreadFactory();
拒绝策略一般使用第4个,谁提交谁执行:
/**
* 当线程需求数量超出预设峰值上限,如何拒绝线程资源获取
* 1、直接丢弃
* 2、替换工作队列的最后一个
* 3、抛异常中断
* 4、哪个线程提交的任务就让那个线程执行
* 5、自定义
*/
ThreadPoolExecutor.DiscardPolicy discardPolicy = new ThreadPoolExecutor.DiscardPolicy();
ThreadPoolExecutor.DiscardOldestPolicy discardOldestPolicy = new ThreadPoolExecutor.DiscardOldestPolicy();
ThreadPoolExecutor.AbortPolicy abortPolicy = new ThreadPoolExecutor.AbortPolicy();
ThreadPoolExecutor.CallerRunsPolicy callerRunsPolicy = new ThreadPoolExecutor.CallerRunsPolicy();
RejectedExecutionHandler handler = (r, executor) -> {
// 入参一个runnable 和 executor
};
Spring封装的线程池:
任务执行器
1、不需要设置队列类型,但是要提供队列长度
2、可以设置线程名称前缀
3、当所有任务执行完毕时,释放线程池资源
4、需要调用初始化方法
ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
executor.setCorePoolSize(corePoolSize);
executor.setMaxPoolSize(maximumPoolSize);
executor.setQueueCapacity((int)(maximumPoolSize * 1.5D));
executor.setKeepAliveSeconds(60);
executor.setThreadNamePrefix("线程名称前缀");
executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());
executor.setWaitForTasksToCompleteOnShutdown(true); /* 等待所有任务结束后再关闭线程池 */
executor.initialize();
要设置手动释放资源,就不要使用Spring注册成Bean配置了,那这个线程池就是临时在业务方法需要调用一下
【Java】线程池配置的更多相关文章
- 【Java 并发】Executor框架机制与线程池配置使用
[Java 并发]Executor框架机制与线程池配置使用 一,Executor框架Executor框架便是Java 5中引入的,其内部使用了线程池机制,在java.util.cocurrent 包下 ...
- Java 线程池框架核心代码分析--转
原文地址:http://www.codeceo.com/article/java-thread-pool-kernal.html 前言 多线程编程中,为每个任务分配一个线程是不现实的,线程创建的开销和 ...
- Java线程池使用说明
Java线程池使用说明 转自:http://blog.csdn.net/sd0902/article/details/8395677 一简介 线程的使用在java中占有极其重要的地位,在jdk1.4极 ...
- (转载)JAVA线程池管理
平时的开发中线程是个少不了的东西,比如tomcat里的servlet就是线程,没有线程我们如何提供多用户访问呢?不过很多刚开始接触线程的开发攻城师却在这个上面吃了不少苦头.怎么做一套简便的线程开发模式 ...
- 四种Java线程池用法解析
本文为大家分析四种Java线程池用法,供大家参考,具体内容如下 http://www.jb51.net/article/81843.htm 1.new Thread的弊端 执行一个异步任务你还只是如下 ...
- Java线程池的几种实现 及 常见问题讲解
工作中,经常会涉及到线程.比如有些任务,经常会交与线程去异步执行.抑或服务端程序为每个请求单独建立一个线程处理任务.线程之外的,比如我们用的数据库连接.这些创建销毁或者打开关闭的操作,非常影响系统性能 ...
- Java线程池应用
Executors工具类用于创建Java线程池和定时器. newFixedThreadPool:创建一个可重用固定线程数的线程池,以共享的无界队列方式来运行这些线程.在任意点,在大多数 nThread ...
- [转 ]-- Java线程池使用说明
Java线程池使用说明 原文地址:http://blog.csdn.net/sd0902/article/details/8395677 一简介 线程的使用在java中占有极其重要的地位,在jdk1. ...
- Java 线程池框架核心代码分析
前言 多线程编程中,为每个任务分配一个线程是不现实的,线程创建的开销和资源消耗都是很高的.线程池应运而生,成为我们管理线程的利器.Java 通过Executor接口,提供了一种标准的方法将任务的提交过 ...
- java线程池的使用与详解
java线程池的使用与详解 [转载]本文转载自两篇博文: 1.Java并发编程:线程池的使用:http://www.cnblogs.com/dolphin0520/p/3932921.html ...
随机推荐
- 【Effective C++】设计与声明——reference篇
以pass-by-reference-to-const替换pass-by-value 缺省情况下C++以by value方式传递对象至(或来自)函数.除非你另外指定,否则函数参数都是以实际实参的复件( ...
- vue3+vant 引入Dialog Toast都会失败报错not defined
今天在封装vant组件的时候,刚好要用到toast提示信息的组件,索性就按照官网提供的引入方法进行正常的引入,嘿,好家伙,一顿操作下来后发现竟然报Toast未定义,这就纳闷了,明明步骤都是对的啊,所以 ...
- Qt QMainWindow的使用
参考视频:黑马科技:https://www.bilibili.com/video/BV1XW411x7NU?p=19 QMainWindow是一个为用户提供主窗口程序的类,包含一个菜单栏(menu b ...
- 前端传参中文需要utf-8转一下给后端
const Msg = this.form.Msg.replace( (/%(u[0-9A-F]{4})|(%[0-9A-F]{2})/gm, $0 => { return escape($0) ...
- kettle从入门到精通 第三十二课 mysql 数据连接集群/分区配置
1.这里的集群实际上是数据分区或者分片的概念,如中国全国的学生,应该不会都存在一张表里面,有可能每个省市一个表进行存储. 2.集群(分区),如下图所示 设置在"集群"标签,勾选&q ...
- 硬件开发笔记(十七):RK3568底板电路串口、485、usb原理图详解
前言 原理图有一些常用电路. 本篇就将集中常用电路分析完,如uart口,涉及usart串口.rs485.usb口. 串口 串行接口简称串口,也称串行通信接口或串行通讯接口(通常指COM接 ...
- 什么是 MyBatis 的接口绑定,有什么好处?
接口映射就是在 MyBatis 中任意定义接口,然后把接口里面的方法和 SQL 语句绑定,我们直接调用接口方法就可以,这样比起原来了 SqlSession 提供的方法我们可以有更加灵活的选择和设置.
- StringUtils.join()方法使用
* StringUtils.join()方法使用 打印输出: * 使用 StringBuilder 进行拼接:张三,李四,王五 * 使用 StringUtils.join 进行拼接:张三,李四,王五 ...
- 免费且离线的同声翻译利器「GitHub 热点速览」
开源的翻译软件众多,但大多数依赖于翻译 API 服务,因此就需要联网.有次数限制.并非完全免费.然后,本周上榜的是一款可以离线使用的 Android 翻译软件:RTranslator,它创建于 4 年 ...
- 详解Web应用安全系列(3)失效的身份认证
大多数身份和访问管理系统的设计和实现,普遍存在身份认证失效的问题.会话管理是身份验证和访问控制的基础,并且存在于所有有状态的应用程序中.攻击者可以使用指南手册来检测失效的身份认证,但通常会关注密码转储 ...