请考虑我们的代码如下:
Object obj = true ? new Integer(0) : new Long(1);
System.out.println(obj.getClass() + "\nvalue = " + obj);
结果是:
class java.lang.Long
value = 0
而不是:
class java.lang.Integer
value = 0
有人可以澄清为什么我们在Java中有这样的功能吗?这对我来说很奇怪。 你有什么例子可以用它吗?
更新: 这是一段字节码,我们可以看到,那里有什么
NEW java/lang/Integer
DUP
LDC "0"
INVOKESPECIAL java/lang/Integer.<init> (Ljava/lang/String;)V
INVOKEVIRTUAL java/lang/Integer.intValue ()I
I2L
INVOKESTATIC java/lang/Long.valueOf (J)Ljava/lang/Long;
ASTORE 1
答案 0 :(得分:12)
这里发生的是
的结果Long
和long
类型转换为Integer
,以用作应用于条件运算符表达式的公共类型条件运算符的第二个和第三个操作数必须最终具有相同的类型,这是表达式的结果类型。当然,Long
和Integer
不是同一类型。
但是,如JLS§15.25中所述,编译器在确定要应用于表达式的可能公共类型时将应用binary numeric promotion。该部分有一个方便的表15.25-D,告诉我们当第二个操作数的类型为Long
且第三个操作数的类型为Integer,Long
时,编译器将对{{1}进行二进制数字提升}。 Integer,Long
上的二进制数字促销产生long
。因此条件运算符表达式的结果是long
。
由于表达式的结果类型为long
,因此Integer
或Long
必须取消装箱(然后在Integer
的情况下进行投射)。
最后,您将其分配给强制装箱的Object
,并将long
包裹在Long
中。因此,您最终得到的Long
包含与您的输出相匹配的值0
。
如此有效,如果我们忽略了编译器将优化以下一半的事实,因为它处理一个常量表达式,这要归功于代码中的true
(我已经使用过{在下面的{1}},代码最终是这样的:
flag
Object obj = Long.valueOf(flag ? (long)(new Integer(0)).intValue() : (new Long(1)).longValue());
System.out.println(obj.getClass() + "\nvalue = " + obj);
表示将(long)(new Integer(0)).intValue()
拆箱并将其投放到Integer
,以便它与表达式结果类型匹配。long
表示取消装箱(new Long(1)).longValue()
,因此 与表达式结果类型相匹配。Long
代表拳击结束。答案 1 :(得分:4)
JLS - 15.25. Conditional Operator ? ::
中详细说明了这种行为条件运算符有三个操作数表达式。 第一个和第二个表达式之间出现
?
,第二个和第三个之间出现:
/ em>表达。[...]
条件表达式的类型确定如下:
答案 2 :(得分:0)
实际上long可以存储整数的值,但是整数不能存储long的值(Concept正在加宽),而是将它存储在Object中,这就是它将它存储在Long中的原因。在内部,它也使用装箱和拆箱
可能的编译器代码:
Long obj = true ? new Integer(0) : new Long(1);
System.out.println(obj.getClass()+“\ nvalue =”+ obj);
不能正常工作的代码(无法编译):
Integer obj = true ? new Integer(0) : new Long(1);
System.out.println(obj.getClass()+“\ nvalue =”+ obj);
自己检查并告诉我你是否对此有任何疑问。
答案 3 :(得分:0)
这与三元运算符的工作原理有关。
:
两侧的操作数必须是兼容的类型,所以你不能这样:
true ? 1 : "Hello"
由于int
和String
不能相互隐含地转换。
但是,在您的情况下,类型 兼容! int
可以隐式转换为long
。这就是编译器的作用!它看到了一个int和一个long,并决定表达式应该计算为long
。它会将这两个值取消装箱,并将int
隐含地转换为long
。最后,它会将结果long
打包,以便它变为Long
并将其放入变量中。