anzu
V2EX  ›  Java

为什么会有这种类型转换

By anzu at 2021 年 1 月 25 日 · 2418 次点击
    private static Integer getInteger() {
        return null;
    }

    public static void main(String[] args) {
        boolean condition = false;
        // error: null pointer exception
        Integer i = condition ? 1 : getInteger();
        if (Objects.equals(i, 1)) {
            System.out.println("i == 1");
        } else {
            System.out.println("i == null");
        }
    }

为什么是 getInteger() 返回值退化成 int 而不是 1 提升为 Integer ?

第 1 条附言  ·  2021 年 1 月 25 日

我懂了!

找到了相关 specs,下面链接的表格罗列了当 Conditional Operator 遇到不同类型的2号位与3号位时,如何进行类型转换的所有情况,可怕。

https://docs.oracle.com/javase/specs/jls/se8/html/jls-15.html#jls-15.25

对于本例,无论 1 或 Integer 在2号位还是3号位,整个表达式的值类型都将转换成 int,由于表达式结果赋值给 Integer 变量,所以最后还会进行一层隐式转换。

4 条回复  •  2021-01-25 20:23:59 +08:00
mgzu
   1
mgzu  
   2021 年 1 月 25 日
用 JD-GUI 看到的反编译结果是
Integer i = Integer.valueOf(condition ? 1 : getInteger().intValue())
AoEiuV020
   2
AoEiuV020  
   2021 年 1 月 25 日
还真没注意过这情况,确实有点不友好,出来本来可以避免的空指针,
不过从一开始我记得的就是 Integer 参与运算会拆箱,int 参与泛型会装箱,
倒是没有违反我的记忆,
Bronya
   3
Bronya  
   2021 年 1 月 25 日
楼主你发的链接里,bnp(..) T | bnp(..) lub(..) 分别是什么意思呀?
~~翻译了一下没看太明白🤪~~
AoEiuV020
   4
AoEiuV020  
   2021 年 1 月 25 日
啊这,有点宁信度了,代码都跑过了,确实是拆箱,那设计上当然就是拆箱,白皮书当然写着拆箱,不看出知道吧,
© 2026 V2EX · 25ms · 3.9.8.5