Reputation: 365
I have a question about the promotion of primitive types in Java. As we can see in the following example, one of the methods does not compile due to an error of type mismatch. Each method returns the same value but in different types.
The version of primitive long
method works without error while the version of wrapper class Long
fails. This is because the int
literal in the return
statement will be first promoted to a broader primitive type (e.g. long
) and then to the corresponding wrapper class Integer
and so on. Since Integer
is not a subclass of Long
the compiler gives an error.
But why does the version of wrapper class Byte
works without any error? What exactly does the compiler do at this point?
long getPrimitiveLong() {
return 12; // valid
}
Long getWrapperLong() {
return 12; // Error: type mismatch
}
Byte getWrapperByte() {
return 12; // valid
}
Upvotes: 4
Views: 1540
Reputation: 1344
This is because Java allows 1 conversion or Autoboxing, not more.
Java can do all these:
int i = 5;
double d = i; // int to double
long l = i; // int to long
long l = d; // double to long
Or autobox:
Integer i = 5; // int to Integer
Double d = 5.0; // double to Double
Long l = 5L; // long to Long
Converting twice, say int to Double, gives Java a hard time.
Upvotes: 4
Reputation: 4987
As a short answer - try to replace 12 with 128 (byte is in range -128 to 127). It won't compile, right? The outcome here is that the compiler knows about byte boundaries.
For the in-depth answer you can do a deep dive into OpenJDK.
Upvotes: 0
Reputation: 726509
The version with Byte
works through some compiler magic.
Unlike long
numeric literals which can be constructed with a L
suffix, e.g. 12L
, there is no such thing as a byte
literal. That is why Java compiler treats numeric literals that fit in a byte as byte
literals. Hence, 12
in your last example is considered a constant of type byte
.
Java Language Specification offers a description of this conversion in section 5.2:
A narrowing primitive conversion followed by a boxing conversion may be used if the type of the variable is:
Byte
and the value of the constant expression is representable in the typebyte
.Short
and the value of the constant expression is representable in the typeshort
.Character
and the value of the constant expression is representable in the typechar
.
Upvotes: 7
Reputation: 7591
number like 12 consider as int by default by the compiler that is why the error
To fix that you can use casting for byte and place L after the value of long variable.
Read following post for more details
http://javaseeeedu.blogspot.com/2015/12/casting-part-1.html
Upvotes: 0