• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Jeanne Boyarsky
  • Ron McLeod
  • Paul Clapham
  • Liutauras Vilda
Sheriffs:
  • paul wheaton
  • Rob Spoor
  • Devaka Cooray
Saloon Keepers:
  • Stephan van Hulst
  • Tim Holloway
  • Carey Brown
  • Frits Walraven
  • Tim Moores
Bartenders:
  • Mikalai Zaikin

Type casting byte to Integer compile error

 
Greenhorn
Posts: 29
IntelliJ IDE PHP Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator


Any ideas why first one works but second one fails?
 
author
Posts: 23951
142
jQuery Eclipse IDE Firefox Browser VI Editor C++ Chrome Java Linux Windows
  • Likes 1
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Murat Kutluer wrote:
Any ideas why first one works but second one fails?



It's a weird artifact of section 5.2 of the Java Language Specification...

https://docs.oracle.com/javase/specs/jls/se8/html/jls-5.html#jls-5.2

That section of the specification does not list implicit casting followed by boxing (auto) as an option. And hence, the second case is a compile error.

As for the first case, interestingly, there is a clause that covers that. It is a bit further down on that section, and applies to compile time constants. And interestingly, it only applies to narrowing followed by boxing.
           
Henry
 
Ranch Hand
Posts: 234
12
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
There is no compiler error.
 
Murat Kutluer
Greenhorn
Posts: 29
IntelliJ IDE PHP Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Henry,

I think you meant this one. As you said there is nothing about Integer and Long and Integer and Long generate compile error.


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 type byte.
  • Short and the value of the constant expression is representable in the type short.
  • Character and the value of the constant expression is representable in the type char.





  • Hi Daniel, there are compile errors on second and third lines. I checked it many times.
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    Murat Kutluer wrote:Hi Daniel, there are compile errors on second and third lines. I checked it many times.


    That's strange. Your original code compiles just fine on my system. I'm using Eclipse with a Java 7 JDK.
     
    Murat Kutluer
    Greenhorn
    Posts: 29
    IntelliJ IDE PHP Java
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    I'm using JDK 8. I also checked it on online compiler.

    http://www.tutorialspoint.com/compile_java_online.php
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    I just noticed that my Eclipse compiler configuration for problems with boxing and unboxing conversions was set to "ignore"
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    Daniel Cox wrote:I just noticed that my Eclipse compiler configuration for problems with boxing and unboxing conversions was set to "ignore"


    After doing some digging, I found out that my Eclipse IDE allows the code to compile due to a bug in the Eclipse compiler. I’m using Eclipse Indigo with JDK 1.7 compliance. It has nothing to do with the configuration to flag boxing/unboxing code as a warning or error (by default, this is set to "ignore").
     
    Murat Kutluer
    Greenhorn
    Posts: 29
    IntelliJ IDE PHP Java
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Have you tried the command line? I changed the JDK version to 7 of IntelliJ, I got the same result.
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Yes. I get a compiler error when I use the command line but no compiler error when I use my Eclipse IDE.

    In my Eclipse IDE, this code compiles just fine when it shouldn't.

     
    Murat Kutluer
    Greenhorn
    Posts: 29
    IntelliJ IDE PHP Java
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    It is weird to see that Eclipse works different than JDK.
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Likes 1
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    It does happen. Eclipse doesn't use javac. It uses its own special compiler that is able to compile code as you type code. This webpage discusses autoboxing issues in Eclipse 3.4 (JDK compliance 1.5) - autoboxing code that doesn't compile in javac does compile in Eclipse 3.4 (JDK compliance 1.5).
     
    Ranch Hand
    Posts: 53
    1
    Oracle Java
    • Likes 1
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator


    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 type byte.
    Short and the value of the constant expression is representable in the type short.
    Character and the value of the constant expression is representable in the type char.




    Thanks everyone for information, However i would like to add some point here.

    1-Integer , Short , Byte and Long all the wrapper classes and all are child of Number class.But they are not related each other. (i do not know why ?)
    2-And as all know all the whole number operation perform on int or long type. so it mean they automatically promoted to higher level (compiler does this task.).
    3-As long as it is primitive type operation it is easy to understand and remember , example lineA: this will not compiler error incompatible types: possible lossy conversion from int to byte.
    lineB: This will also work , because of final special modifier.

    4-And char is work differently , since it whole positive integer therefore you can directly assign value to char variable.
    5-Let see the Auto boxing and unboxing line1: incompatible types: Integer cannot be converted to byte. this mean the compiler will not Convert Integer Object to byte primitive type. it can only convert to int primitive type. It is because of point 1. There is no relationship between wrapper class however primitive type has some relation.
    line2: This line also not compile. ideally i thought this should compile , because wrapper class are immutable . once you declare you can not change them. However it does not work.
    line3: this compile and run.
    line4: this will not work ,let understand this i will converted to int type without any issue, but you can not able to convert int primitive to Byte class.  no relation.
    line5: this will work without any issue.
    line6: this will work because 100 is byte and byte will automatically converted to Byte object.
    line7: this will compile . Since i is Integer which is sub class of Number so you can convert to Number and Number is also sub class of Byte so downcast as well. Same as any object which you promote to Object class.
    but in run time it will throw error.
    java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.Byte
           at IntExample.main(IntExample.java:8)
     
    Henry Wong
    author
    Posts: 23951
    142
    jQuery Eclipse IDE Firefox Browser VI Editor C++ Chrome Java Linux Windows
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    First, read this topic regarding compile time constants, as I will be referring to it...

    https://coderanch.com/t/454384/java/java/compile-time-constant

    prateek shaw wrote:
    3-As long as it is primitive type operation it is easy to understand and remember , example



    Two issues. One. "Easy to understand and remember" is relative. What is easy for someone may not be for another. This isn't really clear as a definition.

    And two... "because of final special modifier" isn't correct. It is possible to have the final specifier, and for it to still not work.

    Anyway, this works because section 5.2 (see above) has a section allow for compile time constants. And in this example, the expression is a compile time constant (see included link for details).

    Henry                            
     
    Henry Wong
    author
    Posts: 23951
    142
    jQuery Eclipse IDE Firefox Browser VI Editor C++ Chrome Java Linux Windows
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    prateek shaw wrote:



    This line doesn't compile because the right hand side expression is not a compile time constant (as of the latest version of the JLS, wrapper classes are not treated as compile time constants). And since it is not a compile time constant, it can't use the special clause of section 5.2 to be implicitly narrowed from an int to a byte.

    Henry
     
    Henry Wong
    author
    Posts: 23951
    142
    jQuery Eclipse IDE Firefox Browser VI Editor C++ Chrome Java Linux Windows
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    prateek shaw wrote:



    Line 7 is actually not clear, as you did not show the declaration and initialization of the i variable. However, I will speculate that the variable is not a compile time constant, and hence, it is why line 7 does not compile. If the variable had been a compile time constant, then line 7 should compile (and work) fine.

    Henry
     
    Bartender
    Posts: 1251
    87
    Hibernate jQuery Spring MySQL Database Tomcat Server Java
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    Henry Wong wrote:

    prateek shaw wrote:



    Line 7 is actually not clear, as you did not show the declaration and initialization of the i variable. However, I will speculate that the variable is not a compile time constant, and hence, it is why line 7 does not compile. If the variable had been a compile time constant, then line 7 should compile (and work) fine.

    Henry

    I think on line no 7he mistakenly typed i instead of i1, where i1 is Integer i1= 100; If that is the case then although i1 is declared final It will not compile because can not cast from int to Byte

    prateek shaw wrote:

    I assume It is i1 not i then It will compile but will give runtime exception ClassCastException says Integer cannot be cast to Byte.
     
    prateek shaw
    Ranch Hand
    Posts: 53
    1
    Oracle Java
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Thanks Henry Wong for your feedback totally appreciated.


    This line doesn't compile because the right hand side expression is not a compile time constant (as of the latest version of the JLS, wrapper classes are not treated as compile time constants). And since it is not a compile time constant, it can't use the special clause of section 5.2 to be implicitly narrowed from an int to a byte.



    Thanks for clarification. This is new information for me.
     
    Greenhorn
    Posts: 11
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Hi for all, sorry if I resume this old topic but there's something I don't understand.



    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 type byte.
    Short and the value of the constant expression is representable in the type short.
    Character and the value of the constant expression is representable in the type char.



    Is there any reason for this or should I learn it as a simple rule? Why the types Integer and Long are not allowed with narrowing + boxing conversion?
    Thanks
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    francisco de feudis wrote:Is there any reason for this or should I learn it as a simple rule? Why the types Integer and Long are not allowed with narrowing + boxing conversion?


    Hello francisco de feudis. I have summarized the rules below.

    The rules for autoboxing a primitive to a Double, Float or Long are:
    • Only a double primitive can be autoboxed to a Double
    Double d = 1D; // compiles
    • Only a float primitive can be autoboxed to a Float
    Float f = 1F; // compiles
    • Only a long primitive can be autoboxed to a Long
    Long l = 1L; // compiles

    The rules for autoboxing a primitive to an Integer, Byte, Short or Character are:
    • An int primitive can be autoboxed to an Integer
    Integer i = 1; // compiles
    • A byte primitive can be autoboxed to a Byte
    byte b = 1;
    Byte b_ = b; // compiles

    • A short primitive can be autoboxed to a Short
    short s = 1;
    Short s_ = s; // compiles

    • A char primitive can be autoboxed to a Character
    char c = 1;
    Character c_ = c; // compiles


    Additional rules for autoboxing a primitive to an Integer, Byte, Short or Character are:
    • A byte, short, or char primitive can be autoboxed to an Integer if it is a compile-time constant
    short s = 1; // not a compile-time constant
    Integer i = s; // compiler error

    final short s = 1; // a compile-time constant
    Integer i = s; // compiles

    • An int, short, or char primitive can be autoboxed to a Byte if it is a compile-time constant and its value is within the byte range. This always happens via an implicit cast (narrowing primitive conversion) to byte followed by boxing to Byte
    char c = 1; // not a compile-time constant
    Byte b = c; // compiler error

    final char c = 1; // a compile-time constant
    Byte b = c; // compiles

    • An int, short, or byte primitive can be autoboxed to a Character if it is a compile-time constant and its value is within the char range. This may happen via an implicit cast (narrowing primitive conversion) to char followed by boxing to Character.
    byte b = 1; // not a compile-time constant
    Character c = b; // compiler error

    final byte b = 1; // a compile-time constant
    Character c = b; // compiles

    • An int, char, or byte primitive can be autoboxed to a Short if it is a compile-time constant and its value is within the short range. This may happen via an implicit cast (narrowing primitive conversion) to short followed by boxing to Short.
    byte b = 1; // not a compile-time constant
    Short s = b; // compiler error

    final byte b = 1; // a compile-time constant
    Short s = b; // compiles



    P.S.
    "may happen" because a byte primitive can never be narrowed.
     
    Murat Kutluer
    Greenhorn
    Posts: 29
    IntelliJ IDE PHP Java
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    This one is wrong, second line generate compile error.

     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Thanks for pointing that out Murat Kutluer. It’s my silly Eclipse compiler again. I’ve modified the rules below.

    The rules for autoboxing a primitive to a Double, Float, Long or Integer are:
    • Only a double primitive can be autoboxed to a Double
    Double d = 1D; // compiles
    • Only a float primitive can be autoboxed to a Float
    Float f = 1F; // compiles
    • Only a long primitive can be autoboxed to a Long
    Long l = 1L; // compiles
    • Only an int primitive can be autoboxed to an Integer
    Integer i = 1; // compiles

    Please ignore this rule
    • A byte, short, or char primitive can be autoboxed to an Integer if it is a compile-time constant
     
    francisco de feudis
    Greenhorn
    Posts: 11
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Thanks for exhaustive reply Daniel Cox and Murat Kutluer.

    I'm still thinking about this lines regarding narrowing + autoboxing:



    I don't understand why only Byte, Short and Character are allowed to use narrowing + autoboxing, why Long and Integer are excluded.
    I just would know is behind this choice done by the Java language engineer (if it is a choice). There's something I don't know.


    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 type byte.
    Short and the value of the constant expression is representable in the type short.
    Character and the value of the constant expression is representable in the type char.



    Thanks again for the help.
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    francisco de feudis wrote:I don't understand why only Byte, Short and Character are allowed to use narrowing + autoboxing, why Long and Integer are excluded.


    The primitive types double, float, long and integer have their own literals (for example, 1D, 1F, 1L, 1).
    The primitive types byte, short, char do not have their own literals.

    The compiler uses a trick to allow you assign an int literal (like 1) to a byte, short or char variable without using an explicit cast. The compiler inserts an implicit cast for you. Any int, byte, short or char compile-time constant that is within range can be assigned to a byte, short or char without an explicit cast because the compiler inserts an implicit cast (if needed). Similarly, any int, byte, short or char compile-time constant that is within range can be assigned to a Byte, Short or Character without an explicit cast or an explicit boxing conversion because the compiler inserts an implicit cast (if needed) followed by an implicit boxing conversion.
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    I noticed a typo in my last post. Java doesn't have an integer primitive type; it has an int primitive type.
     
    francisco de feudis
    Greenhorn
    Posts: 11
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Thanks again for the reply Daniel Cox, I wonder at this point why the compiler can't do this:


    Integer I = (int)(byte) 1; //compile



    Here the cast to int is the implicit cast added by the compiler before to do the autoboxing.
     
    Daniel Cox
    Ranch Hand
    Posts: 234
    12
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator

    francisco de feudis wrote:I wonder at this point why the compiler can't do this:


    Integer I = (int)(byte) 1; //compile




    According to the rules, implicit casting applies only when autoboxing a primitive to a Byte, Short or Character. It doesn't apply when autoboxing a primitive to an Integer.
     
    reply
      Bookmark Topic Watch Topic
    • New Topic