Skip to content

AOT 和 JIT

JDK 17 对 Java 编译技术做了调整。

编译方式回顾

JIT(Just-In-Time)编译

bash
# 传统方式:运行时编译
java -jar app.jar

# 启动后,JIT 编译器把热点代码编译成机器码

特点:

  • 启动慢(需要编译)
  • 运行时优化(性能更好)
  • 内存占用高(JIT 编译器)

AOT(Ahead-Of-Time)编译

bash
# 提前编译:构建时生成机器码
jaotc --output lib.so --class-name MyApp MyApp.class

# 运行时代替 JIT
java -A:lib=lib.so -jar app.jar

特点:

  • 启动快(不需要编译)
  • 无运行时优化(性能可能不如 JIT)
  • 构建时间长

JDK 17 的变化

移除了 jaotc

bash
# JDK 16 及之前
jaotc --output lib.so MyApp.class

# JDK 17
# jaotc 已被移除

原因

  1. GraalVM 的崛起:GraalVM 提供了更好的 AOT 能力
  2. 维护成本:jaotc 维护负担大
  3. Native Image:GraalVM Native Image 是更好的选择

GraalVM Native Image

如果你需要 AOT 编译,使用 GraalVM Native Image:

bash
# 安装 GraalVM
gu install native-image

# 构建原生镜像
native-image -jar app.jar myapp

# 运行(像本地程序一样)
./myapp

Native Image 特点

特性JVMNative Image
启动时间极快
内存占用
预热需要不需要
动态特性支持受限

限制

  • 不支持反射(需要配置)
  • 不支持动态类加载
  • 构建时间长

JIT 改进

虽然移除了 AOT,但 JIT 在持续改进:

JVM CI(JDK 9+)

新的 JIT 编译器接口:

bash
# 使用 GraalVM JIT
java -XX:+UseGraalJIT -jar app.jar

提前编译热点

bash
# JDK 17 改进了分层编译
java -XX:+UseZGC -jar app.jar

选择建议

场景推荐方案
传统服务器应用JVM JIT
微服务/KubernetesGraalVM Native Image
ServerlessGraalVM Native Image
大型单体应用JVM JIT
短生命周期程序GraalVM Native Image

示例:Spring Boot + Native Image

xml
<!-- pom.xml -->
<plugin>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-maven-plugin</artifactId>
    <configuration>
        <image>
            <builder>paketobuildpacks/builder:tiny</builder>
            <env>
                <BP_NATIVE_IMAGE>true</BP_NATIVE_IMAGE>
            </env>
        </image>
    </configuration>
</plugin>

小结

JDK 17 的编译技术变化:

  • 移除了 jaotc:AOT 编译改用 GraalVM
  • GraalVM Native Image:更好的 AOT 方案
  • JIT 持续改进:分层编译更智能

如果你需要快速启动,考虑 GraalVM Native Image;如果需要最佳运行时性能,使用标准 JVM。

基于 VitePress 构建