我正在准备Java 7认证并提出以下问题。
Byte b = 10
编译确定。看起来编译器正在缩小int 10到byte 10然后装箱。怎么会Byte b = new Byte(10)
无法编译?为什么编译器不能像第一种情况那样缩小int 10到byte 10?
同样如何Long l = new Long(10)
编译好,但Long l = 10
失败?
我不清楚它是如何工作的。有人可以提供明确的解释吗?
答案 0 :(得分:19)
Section 5.2 of the JLS涵盖了分配上下文中允许的转换类型。
分配上下文允许使用以下之一:
身份转换(第5.1.1节)
扩大原始转换(第5.1.2节)
扩大参考转换(第5.1.5节)
拳击转换(§5.1.7),可选地后跟扩展参考转换
此外,
此外,如果表达式是byte,short,char或int类型的常量表达式(第15.28节):
如果变量的类型是byte,short或char,则可以使用缩小的基元转换,并且常量表达式的值可以在变量的类型中表示。
如果变量的类型为:
,则可以使用缩小的基元转换,然后进行装箱转换。
字节和常量表达式的值可以在类型字节中表示。
简短,常量表达式的值可以在短类型中表示。
字符和常量表达式的值可以在char类型中表示。
Byte b = 10
编译好,因为10
是一个常量表达式,可以表示为byte
。
Byte b = new Byte(10)
将无法编译,因为10
是int
文字,方法调用转换不会执行原始缩小转换。要调用Byte
构造函数进行编译,您可以明确地将10
强制转换为byte
:
Byte b = new Byte( (byte) 10);
Long l = new Long(10)
编译,因为方法调用转换将执行原始扩展转换,包括从int
到long
。
Long l = 10
将无法编译,因为Java不会特别允许进行扩展转换,然后进行装箱转换,as I discussed in a recent answer。要使其编译,您可以使用long
文字,因此只需要装箱。
Long l = 10L;
答案 1 :(得分:10)
基本规则是:
这些规则解释了为什么Long l = 10
不起作用以及new Byte(10)
。第一个将要求将int literal 10扩展为long
,然后将其装箱,这是不允许的。 (更确切地说,它需要从int
到Long
的转换,JLS 5.1.7没有定义。)第二个要求将int literal 10隐式缩小为{{1 },这是不允许的。
但规则有例外。 JLS 5.2明确允许byte
:
此外,如果表达式是类型为
Byte b = 10
,byte
,short
或char
的常量表达式(第15.28节):
- 如果变量的类型是:则可以使用缩小的基元转换,然后使用装箱转换:
int
,常量表达式的值可在Byte
类型中表示。
(省略了一些不相关的部分)
最后,byte
有效,因为int lite 10 可以自动扩展为10L长。
答案 2 :(得分:1)
10是一个整数文字,你必须向下传播它以将它传递给Byte构造函数。遗憾的是,没有字节文字语法来删除演员。
为什么Long l = new Long(10)编译好但Long l = 10失败?
因为10,一个整数,可以适合长而没有问题。整数不能放入一个字节,因此在这种情况下需要强制转换(扩展转换)。
这个演员也是编译时间,因为它也是一个扩大的转换。 Check out section 5.1.5 in the JLS:
扩展引用转换在运行时从不需要特殊操作,因此决不会在运行时抛出异常。它们只是简单地将引用视为具有某种其他类型,并且在编译时可以证明是正确的。
答案 3 :(得分:1)
字节构造函数采用字节类型或字符串类型。见this
Long的构造函数需要long作为参数。由于long可以采用整数,因此它允许在构造函数中使用。
答案 4 :(得分:1)
我想我有一个解决你问题的方法......
//constructor for Byte class
Byte(byte value){
}
java类型转换有两个规则
现在在你的情况下你试图将int转换为字节,这违反了我们的第二条规则.... 但下面是解决方案
Byte b = new Byte((byte)10);
现在让我们谈谈你的第二个问题......
Long x = 10;//incompatible type
这是自动装箱的问题...... 现在我们都知道autoboxing会自动将原始类型转换为它的包装类。 但是在自动装箱的情况下转换不会发生.... int 转换为整数 字节转换为字节 .. 现在当你将int基本类型赋给Long时,它会给你错误的类型不兼容....... 解决方案
Long x = (long) 10;//works fine....