JIT in Java

2025年3月30日 | 阅读 3 分钟

当我们用任何编程语言编写程序时,都需要将其代码转换为机器可理解的形式,因为机器只理解二进制语言。根据编程语言的不同,编译器也不同。编译器是一种将高级语言转换为机器级代码的程序。Java 编程语言使用的编译器名为javac。它将高级语言代码转换为机器代码(字节码)。JITJVM 的一部分,用于优化应用程序的性能。JIT 代表 Java-In-Time Compiler (即时编译器)JIT 编译也称为动态编译。在本节中,我们将学习Java 中的 JIT 是什么、它的工作原理以及JIT 编译器的阶段

Java 中的 JIT 是什么?

Java 中的JITJVM 的一个组成部分。它将执行性能提高到比以前的水平快很多倍。换句话说,它是一个长时间运行、计算密集型的程序,提供了最佳性能环境。它在编译或运行时优化 Java 应用程序的性能。

JIT in Java

JIT 编译包含两种方法:AOT (Ahead-of-Time compilation,预编译) 和解释执行,用于将代码转换为机器代码。AOT 编译器将代码编译为本地机器语言(与普通编译器相同)。它将 VM 的字节码转换为机器代码。JIT 编译器执行以下优化:

  • 方法内联
  • 局部优化
  • 控制流优化
  • 常量折叠
  • 死代码消除
  • 全局优化
  • 调用站点优化启发式

JIT 编译器的优点

  • 它需要较少的内存使用。
  • 代码优化在运行时完成。
  • 它使用不同级别的优化。
  • 它减少了页面错误。

JIT 编译器的缺点

  • 它增加了程序的复杂性。
  • 代码行数较少的程序无法获得 JIT 编译的好处。
  • 它使用大量缓存内存。

JIT 编译器的工作原理

如果 JIT 编译器环境变量设置正确,JVM 会读取 .class 文件(字节码)进行解释,然后将其传递给 JIT 编译器进行进一步处理。在获取字节码后,JIT 编译器将其转换为本地代码(机器可读代码)。

  • Java Development Kit (JDK) 提供Java 编译器 (javac) 来将 Java 源代码编译成字节码 (.class 文件)。之后,JVM 在运行时加载 .class 文件并将字节码转换为二进制代码(机器代码)。进一步,机器代码由解释器使用。
  • 我们知道,Java 字节码的解释执行会降低本地应用程序的性能。这就是实现 JIT 编译器的原因。JIT 编译器通过将字节码编译成本地机器代码来加速应用程序的性能。
  • 默认情况下,当调用方法时,它就会被启用。JVM 直接调用已编译的方法代码,而不进行解释。它不需要太多内存。

因此,JIT 编译器可以提高本地应用程序的性能。我们可以通过以下流程图来理解 JIT 编译器的运作。

JIT in Java

下图显示了 JIT 编译器与 JREJVM 的功能关系。

JIT in Java

优化级别

也称为优化级别。每个级别提供一定程度的性能。JIT 编译器提供以下优化级别:

  • Cold (冷): 在大型 Java 应用程序启动期间使用。目标是获得最佳的编译代码速度。
  • Warm (温): Java 应用程序启动后,当大多数方法达到调用阈值时就会被编译。
  • Hot (热): 消耗超过 1% 的方法会被安排进行热编译。
  • Very Hot (非常热): 对于那些不是非常热但已经很热的方法,会被安排进行非常热的编译。
  • Scorching (炙热): 消耗超过 5% 的方法会被安排进行炙热编译。

默认的初始优化级别是warm。如果我们选择更热的优化级别,可以获得更好的性能,但会增加内存和 CPU 的开销。

在更高的优化级别,虚拟机使用一个称为采样的线程。它会识别执行时间较长的方法。更高的优化级别包括以下技术:

  • 逃逸分析
  • 部分冗余消除

上述技术使用更多的内存和 CPU 来提高 Java 应用程序的性能。它增加了编译成本,但通过性能得到了补偿。