【问题标题】:Is the execution of statements in the following code changed by compiler optimization? [duplicate]编译器优化是否改变了以下代码中语句的执行? [复制]
【发布时间】:2021-08-29 04:31:13
【问题描述】:

recent related 问题中我发现以下代码

public static void main(String[] args) {
/*1*/        int x;
/*2*/        boolean found = false;
/*3*/        if (!found)
/*4*/            x = -1;

/*5*/        System.out.println(x);
    }

有编译器错误 x 不是 init.(initialized)。我很惊讶编译器无法推理 init。特别是因为这段代码似乎不需要任何运行时推理,如下所示:

  1. 在指示的第 2 行,found 设置为 false
  2. 第 2 行和第 3 行之间没有代码。
  3. 所以到达第 3 行,!found 必然是 true,所以 init 是不可避免的。

我想知道这是否正确。我依稀记得编译器优化可以改变语句的执行顺序。这在这里起作用吗?是否有可能在第 3 行和第 4 行之前到达第 5 行?


环境
openjdk 15.0.2 2021-01-19
OpenJDK 运行时环境(内部版本 15.0.2+7-27)
OpenJDK 64 位服务器 VM(内部版本 15.0.2+7-27,混合模式,共享)
javac 15.0.2 视窗 10

【问题讨论】:

    标签: java compiler-optimization causality internal-compiler-error


    【解决方案1】:

    见我的(迟到的)answer on the other question。规范要求源代码分析。

    这不是按照您建议的方式重新排序代码的情况;这会改变行为,这是被禁止的。

    考虑一般情况:如果在计算完成之前允许使用计算,那么没有什么是可预测的。

    但是,在您的示例中,允许足够智能的编译器将生成的代码优化为(有效地)System.out.println(-1)。这两个变量实际上都不是必需的。

    如果发生这种情况,它不会影响所需的明确分配检查。从逻辑上讲,简化是在验证源代码之后发生的。

    您必须检查生成的字节码才能了解实际发生的情况。此外,在 Java 中,可以通过即时编译为本机代码来“稍后”完成优化。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-04-18
      • 1970-01-01
      • 1970-01-01
      • 2010-12-27
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多