繁体   English   中英

拆箱如何在短路布尔表达式中工作?

[英]How does unboxing work in short-circuited boolean expressions?

我最近尝试运行以下两段代码,并对输出感到惊讶。

第一:

// ...
System.out.println( (Boolean)null || true );
// ...

第二:

// ...
System.out.println( (Boolean)null || false );
// ...

第一个示例导致以下输出:
真正

第二个示例导致以下输出:
线程“main”java.lang.NullPointerException中的异常
在com.blah.main(SanityCheck.java:26)

我原以为这两个例子都会导致空指针异常,因为任何短路都是从左到右应用的。 从布尔值中取消装箱布尔值的尝试应该在逻辑的另一侧或考虑之前失败。

谁能解释这种不一致的行为?

我通过JAD运行类文件,看看优化代码的样子。 对于真实案例:

// ...
System.out.println(true);
// ...

对于虚假案件:

// ...
System.out.println(null.booleanValue());
// ...

我会抨击它。 当编译器试图解释这两个语句时,主要区别在于右侧的true语句不需要用左手布尔值进行计算,而右侧的语句是false。

布尔值是一个Object,因此可以设置为null。 这不是引发异常的地方。 当您尝试对设置为null的Boolean对象执行操作时,将引发NullPointerException。 在真实情况下,编译器会将cast null传递给布尔值,并且因为OR与true将始终产生true,条件为true。 在false的情况下,编译器会再次将cast null传递给Boolean,然后检查false,如果条件为false,则需要使用Boolean计算OR,因为条件最终可能为true或false。 计算发生时,抛出NullPointerException。

我无法重现你的结果。 我实际上得到两个案件的NPE。

根据JLS,始终首先评估左侧操作数表达式。 当计算(Boolean)null ,将对null Boolean对象执行自动取消装箱。 特别是,底层代码null.booleanValue()正在导致NPE。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM