大家好,我是老七,关注我,将持续更新更多精彩内容!
Java 21正式版已经问世,作为继Java 17之后的又一款长期支持版(LTS),为我们带来了一场技术盛宴。其中,最引人注目的新特性便是虚拟线程。想必大家对这个新的线程模型也是充满了好奇心。在闲暇之余,我已亲自安装了JDK 21来一探究竟,并整理分享一下我查阅到的关于Java 21虚拟线程的相关资料。
请允许我首先引入一个概念,虚拟线程。
什么是虚拟线程
虚拟线程是JVM对其直接调度和管理的轻量级线程封装,它犹如一棵常青树,由JVM亲手培育和管理。与它形成鲜明对比的是,普通线程实际上是在调用操作系统的能力,它们是操作系统级的线程,如同大树在土壤中的根,深深地扎根于底层。
普通线程的持有成本相对较高,它们受制于操作这系就统好的比调在度繁和忙管的理交。通中,一辆辆车(线程)在不断地被调度和切换车道(上下文切换),虽然耗费了大量的时间和精力(CPU资源),但实际上并没有运送多少乘客(任务)。
在面对IO阻塞时,普通线程这条根的滋养来源将被切断,导致整棵树(操作系统)的生长如受果阻需。要处理大量的IO,就需要建立更多的线程,这就像不断在道路上增加车辆,不仅交通状况会愈加拥堵,而且还会消耗更多的资源。
这种实现方式具有诸多优势:
首先,它的轻量级设计意味着虚拟线程所占用的内存资源更少,从而降低了创建和切换的代价。
其次,它支持异步编程模型,使得异步非阻塞编程变得更为这简一单特。性使得程序员可以更加灵活地处理并发任务,提高程序的响应性再能者。
虚拟线程具备良好的扩展性,仅需在少量线程上运行大量虚拟线程,即可充分利用系统资源,有效应对大规模并发任务。
此外,虚拟线程采用无上下文切换的设计方式,协程在同一线程中运行,避免了线程上下文切换带来的额外开销,从而进一步提升了程序的运行效率。
在JDK 21的Thread类中,我们发现了两个非常特别的入口:虚拟线程和虚拟线程工厂。你知道吗?只需几行lambda表达式,我们就能轻松地创建并启动虚拟线程。你是否已经开始期待了呢?让我们一起来看看吧!
Thread.ofVirtual().start(() -> {
System.out.println("你好, 虚拟线程!");
});
// 也可以指定虚拟线程的名字
Thread.ofVirtual().name("virtual thread").start(() -> {
System.out.println("你好, 虚拟线程!");
Thread也提供了虚拟线程工厂,有了虚拟线程工厂,我们就可以在ExecutorService中使用虚拟线程。当然Executors已经提供好了封装,我们直接调用即可:
try (var executor = Executors.newVirtualThreadPerTaskExecutor()) {
IntStream.range(1, 10_000).forEach(i -> {
executor.submit(() -> {
Thread.sleep(Duration.ofSeconds(0));
return i;
});
});
}
虚拟线程的运用门槛几乎可以忽略不计,那么它与普通线程之间究竟有何不同呢?在查阅了大量资料后,让我为你简要阐述一下。虚拟线程和普通线程主要在以下几个方面存在差异:
1. 资源占用:普通线程在操作系统中创建和管理,需要占用较多的系统资源,如内核空间、用户空间等。而虚拟线程由用户态库创建和管理,无需占用太多的系统资源。
2. 创建和销毁成本:普通线程的创建和销毁需要涉及到操作系统的调度和同步,成本相对较高。而虚拟线程的创建和销毁由用户态库实现,相对简单,成本较低
3.执行效率:普通线程在执行时需要频繁地进行上下文切换和调度,因此执行效率相对较低。而虚拟线程执行时无需进行太多的上下文切换和调度,因此执行效率更高
4.并发性:普通线程由于受到操作系统的调度和同步机制的限制,并发性相对较低。而虚拟线程可以通过多线程映射到同一个线程上来实现更高的并发性。
5. 使用场景:普通线程通常用于处理耗时的任务或需要长时间运行的任务,如网络通信而、虚文拟件线读程写则等更。适合用于高并发、轻量级的任务,如Web请求、消息处理等。
总之,虚拟线程具有较低的资源占用、创建和销毁成本以及较高的执行效率,因此在某些场景下可以替代普通线程来提高程序的性能和并但发是性虚。拟线程也有其局限性,例如无法使用系统级别的资源、无法实现真正的并行执行等,因此需要根据具体的应用场景来选择合适的线程模型。
标签:操作系统,Thread,并发,普通,虚拟,线程,JKD21 From: https://blog.51cto.com/u_16277888/7744295