为什么自动装箱在 eclipse 中起作用,但在 javac 中不起作用?

2022-09-02 22:18:51

此代码:

Integer ints[] = new Integer[]{'1', '2', '3'};

在 eclipse 中编译得很好,但是 javac(版本 1.6.0_27 和 1.7.0)给出了以下错误:

BoxTest.java:4: incompatible types
found   : char
required: java.lang.Integer
               Integer ints[] = new Integer[]{'1', '2', '3'};

BoxTest.java:4: incompatible types

为什么?

我假设它是某种编译器标志,但是挖掘槽日食来弄清楚它并不完全是直截了当的。


答案 1

什么不是在做,不是自动装箱,而是自动投射。在它编译为:javacjavac

Integer ints[] = new Integer[] { (int) '1', (int) '2', (int) '3' };

同样的事情也发生在一个,再次在,我必须做显式转换来编译:Integerjavac

Integer a = (int) '1';

但这是我的发现。从命令行使用Eclipse JDT批处理编译器,即使没有强制转换,它也可以工作:

$ java -jar org.eclipse.jdt.core_3.7.1.v_B76_R37x.jar -classpath rt.jar \
  -1.6 Appo.java 

我已经研究了javac的选项,我认为没有任何方法可以改变这种行为。

我必须推断,这种差异是由Eclipse内部不使用javac,而是JDT编译器引起的。


答案 2

正如 stivlo 已经指出的那样,Eclipse JDT 编译器静默地将代码视为:

Integer refI = Integer.valueOf((int)'a');

但是Java语言规范在第5.2章中说(强调我的):

将表达式的值 (§15.26) 赋值分配给变量时,会发生赋值转换:表达式的类型必须转换为变量的类型。分配上下文允许使用以下方法之一

* an identity conversion (§5.1.1)
* a widening primitive conversion (§5.1.2)
* a widening reference conversion (§5.1.5)
* a boxing conversion (§5.1.7) optionally followed by a widening reference conversion
* an unboxing conversion (§5.1.8) optionally followed by a widening primitive conversion.

强制转换是第一次转换,是第二次转换。编译器通过仅允许一次转换来强制执行规则。(int) 'a'Integer.valueOf(int)javac

看来,你在Eclipse JDT编译器中发现了一个错误。


推荐