没有知识,我们就谈不到欣赏。——别林斯基

今天分享一个冷门基础小知识

我们一般使用boolean的类型,使用结构控制语句条件表达式的时候都是这样:

1
2
if (bar) {
}

此处如果是一个基本类型,也就是boolean的时候,完全ok

但如果是一个包装类型的java.lang.Boolean对象,则在barnull的时候,抛出

1
java.lang.NullPointerException

这是因为底层调用了java.lang.Boolean#valueOf(boolean)拆箱

此处

1
2
3
4
@IntrinsicCandidate
public static Boolean valueOf(boolean b) {
return (b ? TRUE : FALSE);
}

由于添加了@IntrinsicCandidate注解,所以会调用其进行自动拆箱

因此如果是Boolean包装类型,则调用

1
2
if (bar) {
}

等同于

1
2
if (Boolean.valueOf(bar)) {
}

建议大家不要使用包装类型作为条件语句表达式,此处sonarlint也提到:

https://rules.sonarsource.com/java/RSPEC-5411/

Avoid using boxed “Boolean” types directly in boolean expressions

当盒装类型 java.lang.Boolean 用作表达式来确定控制流时(如 Java 语言规范 §4.2.5 boolean 类型和布尔值中所述),如果值为 null (如 Java 语言规范 §5.1.8 取消装箱转换中定义),它将抛出 NullPointerException

完全避免此类转换并显式处理 null 值会更安全。

但请注意,对于已经过 null 检查的布尔值,不会引发任何问题。