JDK 线程池
JDK 线程池
线程池参数
在JDK的4种线程池之前, 先介绍一下线程池的几个参数
- corePoolSize 线程池的核心线程数量,
- maximumPoolSize 线程池的最大线程数量
- keepAliveTime 线程被回收的最大空闲时间
- keepAliveTime 的单位(ms、s、...)
- BlockingQueue 任务队列,存放任务
- ThreadFactory 线程工厂
- RejectedExecutionHandler 线程池拒绝策略(当任务过多的时候,线程池拒绝任务的方式)
allowCoreThreadTimeOut 允许核心线程池被回收, 默认 false, so 默认情况下 核心线程并不会被回收掉.
JDK 提供的四种线程池介绍
newFixedThreadPool
固定线程池数量, 核心线程数 = 最大线程数
任务队列: LinkedBlockingQueue(Integer.MAX_VALUE) 无界队列
适用于同时处理固定任务数的场景.
public static ExecutorService newFixedThreadPool(int nThreads) {
// coreThreads = maxThreads
return new ThreadPoolExecutor(nThreads, nThreads,
0L, TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<Runnable>());
}
newCachedThreadPool
核心线程数为0, 最大为 Integer.MAX_VALUE,也就是当任务足够多的时候, 可以无限增加线程.
任务队列: SynchronousQueue 默认传入参数 fair=false, 即处理任务非公平.
适用于处理小任务
public static ExecutorService newCachedThreadPool() {
return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
60L, TimeUnit.SECONDS,
new SynchronousQueue<Runnable>());
}
SynchronousQueue
public SynchronousQueue(boolean fair) {
// fair = true 则会按照FIFO先入先出的顺序执行
// fair = false 则优先取出最新添加的任务, 如果任务多的话,最先添加的任务反而执行不到
transferer = fair ? new TransferQueue<E>() : new TransferStack<E>();
}
newSingleThreadExecutor
单个线程的线程池
任务队列: LinkedBlockingQueue 同样是无界队列
适用于需要将任务按顺序执行的时候
public static ExecutorService newSingleThreadExecutor() {
// 核心线程数=最大线程数=1
return new FinalizableDelegatedExecutorService
(new ThreadPoolExecutor(1, 1,
0L, TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<Runnable>()));
}
newScheduledThreadPool
固定核心线程数, 线程数量不会再增长, maximumPoolSize 这个参数对定时线程池没有作用.
任务队列: DelayedWorkQueue 无界队列, 这是 ScheduledThreadPoolExecutor 的一个内部类
适用于有延时 或者定时需求的场景
public ScheduledThreadPoolExecutor(int corePoolSize) {
super(corePoolSize, Integer.MAX_VALUE, 0, NANOSECONDS,
new DelayedWorkQueue());
}
线程拒绝策略
AbortPolicy
拒绝新任务,并且抛出异常, 默认的拒绝策略
public static class AbortPolicy implements RejectedExecutionHandler {
public AbortPolicy() { }
public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
// 直接抛出异常
throw new RejectedExecutionException("Task " + r.toString() +
" rejected from " +
e.toString());
}
}
CallerRunsPolicy
当拒绝任务的时候,由调用线程处理该任务.
public static class CallerRunsPolicy implements RejectedExecutionHandler {
public CallerRunsPolicy() { }
public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
// 如果线程池未停止
if (!e.isShutdown()) {
// 当前线程直接调用任务的run方法
r.run();
}
}
}
DiscardPolicy
拒绝新任务,静悄悄的将新任务丢弃,而不通知(太坑了吧), 具体看它的代码也是什么事情都没做, 还真的就直接丢弃任务了.
public static class DiscardPolicy implements RejectedExecutionHandler {
public DiscardPolicy() { }
public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
// 任务被拒绝后,啥事情都不干
}
}
DiscardOldestPolicy
当任务满时, 抛弃旧的未处理的任务, 然后重新执行 execute 方法(此过程会重复), 除非 线程池 停止运行, 这种情况任务将被丢弃.具体看代码
public static class DiscardOldestPolicy implements RejectedExecutionHandler {
public DiscardOldestPolicy() { }
public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
// 如果线程池停止, 直接丢弃任务,不做任何处理
if (!e.isShutdown()) {
// 丢弃一个任务队列中的任务
e.getQueue().poll();
// 重新执行被拒绝的任务, 如果再次被拒绝, 则会一直重复这个过程
e.execute(r);
}
}
}
最后
这次的内容到这里就结束了,最后的最后,非常感谢你们能看到这里!!你们的阅读都是对作者的一次肯定!!!
觉得文章有帮助的看官顺手点个赞再走呗(终于暴露了我就是来骗赞的(◒。◒)),你们的每个赞对作者来说都非常重要(异常真实),都是对作者写作的一次肯定(double)!!!
JDK 线程池的更多相关文章
- jdk线程池主要原理
本文转自:http://blog.csdn.net/linchengzhi/article/details/7567397 正常创建一个线程的时候,我们是这样的:new thread(Runnable ...
- JDK线程池和Spring线程池的使用
JDK线程池和Spring线程池实例,异步调用,可以直接使用 (1)JDK线程池的使用,此处采用单例的方式提供,见示例: public class ThreadPoolUtil { private s ...
- 自己动手写线程池——向JDK线程池进发
自己动手写线程池--向JDK线程池进发 前言 在前面的文章自己动手写乞丐版线程池中,我们写了一个非常简单的线程池实现,这个只是一个非常简单的实现,在本篇文章当中我们将要实现一个和JDK内部实现的线程池 ...
- jdk线程池ThreadPoolExecutor工作原理解析(自己动手实现线程池)(一)
jdk线程池ThreadPoolExecutor工作原理解析(自己动手实现线程池)(一) 线程池介绍 在日常开发中经常会遇到需要使用其它线程将大量任务异步处理的场景(异步化以及提升系统的吞吐量),而在 ...
- JDK线程池的拒绝策略
关于新疆服务请求未带入来话原因的问题 经核查,该问题是由于立单接口内部没有成功调用接续的 “更新来电原因接口”导致的,接续测更新来电原因接口编码:NGCCT_UPDATESRFLAG_PUT ,立单接 ...
- JDK线程池的使用
转载自:https://my.oschina.net/hosee/blog/614319: 摘要: 本系列基于炼数成金课程,为了更好的学习,做了系列的记录. 本文主要介绍: 1. 线程池的基本使用 2 ...
- juc线程池原理(六):jdk线程池中的设计模式
一.jdk中默认线程池中的代理模式 单例类线程池只有一个线程,无边界队列,适合cpu密集的运算.jdk中创建线程池是通过Executors类中提供的静态的方法来创建的,其中的单例类线程池的方法如下: ...
- JDK线程池的实现
线程池 接口Executor 该接口只有一个方法,JDK解释如下 执行已提交的Runnable 任务的对象.此接口提供一种将任务提交与每个任务将如何运行的机制(包括线程使用的细节.调度等)分离开来的方 ...
- jdk线程池,使用手记
Executors----------------------------------------------Executors------------------------------------ ...
随机推荐
- hitTest练习
业务逻辑1: 底部一个按钮, 按钮的上面有一个View,遮挡在按钮的上面. 点击View时, View接收事件,当发现点击的点在按钮的位置时, 让底部的按钮处理事件. ...
- UNIX系统上的抓包工具tcpdump常用命令说明
tcpdump 介绍 tcpdump采用命令行方式对接口的数据包进行筛选抓取,其丰富特性表现在灵活的表达式上. 不带任何选项的tcpdump,默认会抓取第一个网络接口,且只有将tcpdump进程终止才 ...
- Java用n种方法编写实现双色球随机摇号案例
方法清单 规则 实现方式一 实现方式二 实现方式三 实现方式四 实现方法五 之前我用JavaScript编写过一个实现双色球随机摇号的案例, 点击此处查看,今天我再用Java语言来实现这一效果. 规则 ...
- 一加6刷入kali nethunter
Installing Kali NetHunter On the OnePlus 6 准备工具: adb: https://jingyan.baidu.com/article/22fe7cedf67e ...
- 从服务间的一次调用分析整个springcloud的调用过程(一)
首先我们知道springcloud是一个微服务框架,按照官方文档的说法,springcloud提供了一些开箱即用的功能: 1 分布式/版本化配置 2 服务的注册与发现 3 路由 4 服务到服务之间调用 ...
- Solution -「HDU 1788」CRT again
\(\mathcal{Description}\) Link. 解同余方程组: \[x\equiv m_i-a\pmod{m_i} \] 其中 \(i=1,2,\dots,n\). \ ...
- 神奇!这款 Vue 后台框架居然不用手动配置路由
前言 做 Vue 开发脱离不了路由,尤其是中大型项目,页面多且杂,在配置路由的时候总是会变得逐渐暴躁,因为费时,并且又没有什么太多技术含量,总觉得是在浪费时间. 另外如果接手了别人的项目,当业务有变更 ...
- for循环-嵌套
代码 点击查看[ForNest.java]代码 //package com.d; /** * for循环-嵌套 * @date: 2022.2.24 * 正直角三角形.倒直角三角形.等腰三角形.九九乘 ...
- sql注入之报错注入and boolean注入
1.sql注入之报错注入 正常传参,返回页面正常: 加入' 返回页面报错,出现"zhangsan"' 报错注入使用的函数 在这里我们使用 select updatexml(1,c ...
- 网络测试技术——802.1X_MD5认证(上篇)
一.MD5认证简介 1.认证过程 (1)无隧道 (2)客户端和服务器之间进行 2.单向认证 (1)服务器对客户端认证 3.缺点 (1)用户名明文传输 (2)弱MD5哈希 二.MD5认证过程 1.客 ...