Java 线程池之Jetty 线程池学习总结

简介: Java 线程池之Jetty 线程池学习总结

Java 线程池之Jetty 线程池学习总结

前提

Jetty 11.0.x

为什么是Jetty?

Java提供4中创建线程池的快捷方式

Executors.newFixedThreadPool();
Executors.newCachedThreadPool();
Executors.newSingleThreadExecutor();
Executors.newScheduledThreadPool();

但通常我们很少用这4个工厂方法去创建线程池,而是直接使用ThreadPoolExecutor类构造线程池,因为这些工厂方法最终也是调用这个类来创建线程池的。

众所周知,虽然ThreadPoolExecutor提供了corePoolSizemaximumPoolSize两个参数来控制线程池的基本大小和最大大小,但是这两个参数并不是那么好用:当任务队列采用SynchronousQueue时,通常需要无界的maximumPoolSize;当任务队列采用无界队列时,maximumPoolSize的值又相当于不起作用;当任务队列采用有界队列时,仅在任务队列已满,且未达到maximumPoolSize时才会扩充线程池大小。

既然如此,那有没有一种更简单的实现方案呢?使用该方案,使用者只需要简单的配置下线程池的基本大小和最大大小,程序就可以根据任务的繁忙程度自动调整当前线程数量。答案是有的:Jetty--一个基于Java的web容器,和Tomcat齐名

Jetty线程池介绍

任务处理流程

初始化线程池

程序初始化运行时,会先创建线程池,线程池大小默认为minThreads,也就是说会预先创建minThreads个线程,线程名称格式形如“qtp1076496284-13”

创建线程池时:

  • 如果未指定最大线程数(maxThreads),则默认为 200;
  • 如果未指定最小线程数(minThreads),则默认为 8
  • 如果未指定线程空闲超时时间(idleTimeout),则默认为 60000,即60秒
  • 保留线程数(reservedThreads)默认为 -1
  • 如果未指定任务队列,则默认创建BlockingArrayQueue任务队列,容量大小为 8 x 1024
  • 如果指定的最大线程数小于最小线程数,则抛出异常

线程池扩缩容

  • 当前线程数比最小线程数小,或者没有空闲的线程,且当前线程数(threads )小于最大线程数,则创建线程;
  • idleTimout大于0且当前线程数大于最小线程数,且线程空闲时间超过idleTimeout,则停止线程

注意:程序判断是否存在空闲线程的逻辑是这样的:Net空闲线程数 = 空闲线程数 - 任务队列大小,如果“Net空闲线程数”为负数,则表示不存在空闲线程,即需要更多的线程来处理任务。

任务队列及线程相关定义

queueSize 任务队列大小,即队列中等待被线程执行的任务数。可通过getQueueSize()函数获取。

threads 当前线程池中的线程数,包括已租给内部组件的线程、空闲线程、保留线程,以及正在执行临时作业的线程。threads = readyThreads + leasedThreads + utilizedThreads。 可通过getThreads() 函数获取。

readyThreads 准备执行临时任务的线程数。readyThreads = idleThreads + availableReservedThreads。可通过getReadyThreads()函数获取。

idleThreads 未被保留的空闲线程数。idleThreads = readyThreads - availableReservedThreads。可通过getIdleThreads()函数获取。

reservedThreads 保留的线程数,默认值为-1。可通过getReservedThreads()函数获取。

availableReservedThreads 可用的保留线程。可通过getAvailableReservedThreads()函数获取。

leasedThreads 供内部组件使用,用于执行内部任务的线程。需要线程的Jetty组件(比如网络acceptorsselector)可能会使用ThreadPoolBudget从线程池中租用线程。站在线程池的角度来看,这些被租用的线程是活跃的,但是不能用于执行临时任务,比如一个HTTP请求,或者一个WebSocket帧。QueuedThreadPool有一个ReservedThreadExecutor,该组件会从线程池租用线程,但会让这些线程可用,就像它们是“idle”线程一样。线程池启动后,该值一般是恒定的。可通过getLeasedThreads()函数获取。

minThreads 线程池中的最小线程数。可通过getMinThreads() 函数获取。

maxThreads 线程池中的最大线程数。可通过getMaxThreads() 函数获取。

maxAvailableThreads 可用于执行临时任务的最大线程数。maxAvailableThreads = maxThreads - leasedThreads 可通过getMaxAvailableThreads()函数获取。

utilizedThreads执行临时任务的线程数,可通过getUtilizedThreads()函数获取。utilizedThreads = threads - leasedThreads - readyThreads

utilizationRate = utilizedThreads / maxAvailableThreads 执行临时任务的线程利用率。该值为0.0D则表示线程池未被利用,如果为1.0D则表示线程池被充分利用于执行临时任务。可通过getUtilizationRate() 函数获取。

busyThreads 正在执行内部任务和临时任务的线程数。 busyThreads = utilizedThreads + leasedThreads。可通过getBusyThreads()函数获取。

参考链接

https://www.eclipse.org/jetty/javadoc/jetty-11/org/eclipse/jetty/util/thread/QueuedThreadPool.html

https://gitee.com/Tedgar156/jetty.project/blob/jetty-11.0.x/jetty-util/src/main/java/org/eclipse/jetty/util/thread/QueuedThreadPool.java

目录
相关文章
|
4月前
|
IDE Java 编译器
java编程最基础学习
Java入门需掌握:环境搭建、基础语法、面向对象、数组集合与异常处理。通过实践编写简单程序,逐步深入学习,打牢编程基础。
292 1
|
4月前
|
存储 Oracle Java
java零基础学习者入门课程
本课程为Java零基础入门教程,涵盖环境搭建、变量、运算符、条件循环、数组及面向对象基础,每讲配示例代码与实践建议,助你循序渐进掌握核心知识,轻松迈入Java编程世界。
406 0
|
5月前
|
Java API 容器
Java基础学习day08-2
本节讲解Java方法引用与常用API,包括静态、实例、特定类型方法及构造器引用的格式与使用场景,并结合代码示例深入解析。同时介绍String和ArrayList的核心方法及其实际应用。
178 1
|
4月前
|
负载均衡 Java API
grpc-java 架构学习指南
本指南系统解析 grpc-java 架构,涵盖分层设计、核心流程与源码结构,结合实战路径与调试技巧,助你从入门到精通,掌握高性能 RPC 开发精髓。
461 7
|
4月前
|
设计模式 缓存 安全
【JUC】(6)带你了解共享模型之 享元和不可变 模型并初步带你了解并发工具 线程池Pool,文章内还有饥饿问题、设计模式之工作线程的解决于实现
JUC专栏第六篇,本文带你了解两个共享模型:享元和不可变 模型,并初步带你了解并发工具 线程池Pool,文章中还有解决饥饿问题、设计模式之工作线程的实现
288 2
|
4月前
|
JSON 网络协议 安全
【Java】(10)进程与线程的关系、Tread类;讲解基本线程安全、网络编程内容;JSON序列化与反序列化
几乎所有的操作系统都支持进程的概念,进程是处于运行过程中的程序,并且具有一定的独立功能,进程是系统进行资源分配和调度的一个独立单位一般而言,进程包含如下三个特征。独立性动态性并发性。
260 1
|
4月前
|
JSON 网络协议 安全
【Java基础】(1)进程与线程的关系、Tread类;讲解基本线程安全、网络编程内容;JSON序列化与反序列化
几乎所有的操作系统都支持进程的概念,进程是处于运行过程中的程序,并且具有一定的独立功能,进程是系统进行资源分配和调度的一个独立单位一般而言,进程包含如下三个特征。独立性动态性并发性。
269 1
|
5月前
|
Java
Java基础学习day08-作业
本作业涵盖Java中Lambda表达式的应用,包括Runnable与Comparator接口的简化实现、自定义函数式接口NumberProcessor进行加减乘及最大值操作,以及通过IntProcessor处理整数数组,实现遍历、平方和奇偶判断等功能,强化函数式编程实践。
96 5
|
5月前
|
Java 程序员
Java基础学习day08
本节讲解Java中的代码块(静态与实例)及其作用,深入介绍内部类(成员、静态、局部及匿名)的定义与使用,并引入函数式编程思想,重点阐述Lambda表达式及其在简化匿名内部类中的应用。
175 5
|
5月前
|
Java
Java基础学习day07-作业
本作业包含六个Java编程案例:1)动物类继承与多态;2)加油卡支付系统;3)员工管理类设计;4)学生信息统计接口;5)USB设备控制;6)家电智能控制。综合运用抽象类、接口、继承、多态等面向对象技术,强化Java基础编程能力。
218 3