目录
- 📢什么是进程?
- 🎡什么是线程?
- 🚀进程和线程的区别?
- 🎢Java 线程和操作系统的线程有啥区别?
- 🎖️JDK21的虚拟线程
- 🎯虚拟线程和平台线程的对比
📢什么是进程?
- 进程是程序的一次执行过程,是系统运行程序的基本单位。
- 系统运行一个程序即是一个进程从创建,运行到消亡的过程。
- 在 Java 中,当我们启动 main 函数时其实就是启动了一个 JVM 的进程,而 main 函数所在的线程就是这个进程中的一个线程,也称主线程。
如下图所示,在 Windows 中通过查看任务管理器的方式,我们就可以清楚看到 Windows 当前运行的进程
🎡什么是线程?
- 线程与进程相似,但线程是一个比进程更小的执行单位。
- 一个进程在其执行的过程中可以产生多个线程。
- 与进程不同的是同类的多个线程共享进程的堆和方法区资源,但每个线程有自己的程序计数器、虚拟机栈和本地方法栈,所以系统在产生一个线程,或是在各个线程之间作切换工作时,负担要比进程小得多,也正因为如此,线程也被称为轻量级进程。
- Java 程序天生就是多线程程序,我们可以通过 JMX 来看看一个普通的 Java 程序有哪些线程,代码如下。
public class MultiThread {
public static void main(String[] args) {
// 获取 Java 线程管理 MXBean
ThreadMXBean threadMXBean = ManagementFactory.getThreadMXBean();
// 不需要获取同步的 monitor 和 synchronizer 信息,仅获取线程和线程堆栈信息
ThreadInfo[] threadInfos = threadMXBean.dumpAllThreads(false, false);
// 遍历线程信息,仅打印线程 ID 和线程名称信息
for (ThreadInfo threadInfo : threadInfos) {
System.out.println("[" + threadInfo.getThreadId() + "] " + threadInfo.getThreadName());
}
}
}
上述程序输出如下(输出内容可能不同,不用太纠结下面每个线程的作用,只用知道 main 线程执行 main 方法即可):
[5] Attach Listener //添加事件
[4] Signal Dispatcher // 分发处理给 JVM 信号的线程
[3] Finalizer //调用对象 finalize 方法的线程
[2] Reference Handler //清除 reference 线程
[1] main //main 线程,程序入口
从上面的输出内容可以看出:一个 Java 程序的运行是 main 线程和多个其他线程同时运行
🚀进程和线程的区别?
- Java 中,线程作为最小调度单位,进程作为资源分配的最小单位
- 一个进程之内可以分为一到多个线程
- 进程拥有共享的资源,如内存空间等,供其内部的线程共享
- 线程通信相对简单,因为它们共享进程内的内存
- 线程更轻量,线程上下文切换成本一般上要比进程上下文切换低
🎢Java 线程和操作系统的线程有啥区别?
一句话概括 Java 线程和操作系统线程的关系:
- 现在的 Java 线程的本质其实就是操作系统的线程
线程模型是用户线程和内核线程之间的关联方式,常见的线程模型有这三种:
一对一(一个用户线程对应一个内核线程)
多对一(多个用户线程映射到一个内核线程)
多对多(多个用户线程映射到多个内核线程)
在 Windows 和 Linux 等主流操作系统中,Java 线程采用的是一对一的线程模型,也就是一个 Java 线程对应一个系统内核线程
- Windows 和 Linux 等主流操作系统中就是一一对应
🎖️JDK21的虚拟线程
虚拟线程(Virtual Thread)是 JDK 而不是 OS 实现的轻量级线程(Lightweight Process,LWP),由 JVM 调度。许多虚拟线程共享同一个操作系统线程,虚拟线程的数量可以远大于操作系统线程的数量
- 类似于从一java线程对一操作系统线程转变为多java线程对应一操作系统线程
🎯虚拟线程和平台线程的对比
说明:(不详细描述)
- 适用于IO密集型,计算密集型性能最终还是取决CPU核数
- 可以看到在密集 IO 的场景下,需要创建大量的平台线程异步处理才能达到虚拟线程的处理速度。因此,在密集 IO 的场景,虚拟线程可以大幅提高线程的执行效率,
- 减少线程资源的创建以及上下文切换。
- 吐槽:虽然虚拟线程我很想用,但是我 Java8 有机会升级到 Java21 吗?呜呜