• 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

Mixing of code - raw and generic

 
Ranch Hand
Posts: 183
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Please see the foll code .It mixes generic and non-generic code





Line #1 works fine - lsint is of type List<Integer> . lsint.get(0) should return an Integer
but it returns a String and is printed. How come there is no ClassCastException.

BUT , Line #2 gives ClassCastException. WHY ??

Cannot understand why Line #1 gives no exception whereas Line #2 does.


 
Ranch Hand
Posts: 317
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Remember Generics are only for compile time. At run time generics will be removed and replaced with appropriate casts and you will be able to directly assign the returned object to appropriate object without cast. In you case if you can assign the returned value to Integer object. like



will be converted to



But all this will happen behind the scenes.

In your code you are not assigning the returned value to any object so implicit cast will not be performed here and because system will call the toString method of the argument passed to println() method so the value is being printed,

 
Ranch Hand
Posts: 234
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator


#1 System.out.println(lsint.get(0)); // oracle - OK


above statement will compile correctly because compiler knows lsint is of Integer type and it should have Integer objects.
At run time, since there is no generics type check availale so whatever is there in lsint will print.


#2 for(Object o:lsint); // ClassCastException: String


Again above statement will compile successfully because lsint is a List having Integer objects
But at run time,

will work something like

now get method will return String. That is why you will get ClassCastException.
 
Harpreet Singh janda
Ranch Hand
Posts: 317
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

for(Object o:lsint);



This line will not throw any class cast exception.

It will run fine.
 
Brij Garg
Ranch Hand
Posts: 234
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

This line will not throw any class cast exception.

ClassCastException will be thrown. Please check
 
Harpreet Singh janda
Ranch Hand
Posts: 317
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Here is the code



and here is the output



I think i have not modified the original posted code.

P
 
Brij Garg
Ranch Hand
Posts: 234
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I have executed your code also.
still getting classcastexception.


 
Harpreet Singh janda
Ranch Hand
Posts: 317
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
It's strange.

Could you please post the code and full stack trace for the exception you are getting?
 
Brij Garg
Ranch Hand
Posts: 234
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator



Output....
C:\jdk1.5.0_12\bin>javac testClass.java
Note: testClass.java uses unchecked or unsafe operations.
Note: Recompile with -Xlint:unchecked for details.

C:\jdk1.5.0_12\bin>java testClass
java.lang.ClassCastException: java.lang.String
at testClass.main(testClass.java:13)



Why you think classcastexception shuold not thrown?
 
Harpreet Singh janda
Ranch Hand
Posts: 317
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Strange

The same code is working for me.

The only difference is that i am using jdk1.5.0_06
 
Greenhorn
Posts: 25
Oracle PHP Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I also got the classCastException. I think the error is in here.


Looks like casting does not happen as you expect. In this line, the elements in obj list has not casted to Integer type.
 
Brij Garg
Ranch Hand
Posts: 234
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator


I also got the classCastException. I think the error is in here.
List<Integer> lsint = (List<Integer>)obj;

Looks like casting does not happen as you expect. In this line, the elements in obj list has not casted to Integer type.



No error is in line

only.
 
Manjula Weerasinghe
Greenhorn
Posts: 25
Oracle PHP Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Yeah, it shows the error is in that line.
But the cause for that error lies in


Check carefully. It is because casting has not done for each of object separately in the collection (list) (as we expected).

 
Brij Garg
Ranch Hand
Posts: 234
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator


Check carefully. It is because casting has not done for each of object separately in the collection (list) (as we expected).



try using try-catch block for
you will never get execution control in catch block
 
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

Simran Dass wrote:
Line #1 works fine - lsint is of type List<Integer> . lsint.get(0) should return an Integer
but it returns a String and is printed. How come there is no ClassCastException.



Interestingly, I think line #1 is broken too. If the collection is of type string, then it will return a string and call the println() method that takes a string. However, the compiler thinks it returns Integer and incorrectly routes it to the println() method that takes object. This works at runtime because the println() method that takes object merely calls to string first.

This would have also have failed if there was a method that takes an Integer and does something Integer specific. Or even if autoboxing has taken place.

Henry
 
Simran Dass
Ranch Hand
Posts: 183
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Thanks Brij,Harpreet and Henry.

Henry as you said I passed lsint.get(0) to a method which takes an Integer argument
and what do I get - ClassCastException !!. Wow what an explanation. This System.out
not giving the exception was driving me mad. Thanks once again


 
Ranch Hand
Posts: 62
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Henry Wong wrote:

Simran Dass wrote:
Line #1 works fine - lsint is of type List<Integer> . lsint.get(0) should return an Integer
but it returns a String and is printed. How come there is no ClassCastException.



Interestingly, I think line #1 is broken too. If the collection is of type string, then it will return a string and call the println() method that takes a string. However, the compiler thinks it returns Integer and incorrectly routes it to the println() method that takes object. This works at runtime because the println() method that takes object merely calls to string first.

This would have also have failed if there was a method that takes an Integer and does something Integer specific. Or even if autoboxing has taken place.

Henry




This is what I got from docjar for ArrayList class.


Why is line 338 not throwing an exception in case of lsint.get(0)?

EDIT: I have been thinking why line 338 is not throwing an exception. Is it because generics information doesn't exist during run time? So, lsint.get(0) is returning String. (I tried lsint.get(0).getClass() - returns String). Enhanced for loop is somewhere casting the returned value from iterator's next() (which again is String. Iterator's next() also returns '(E) elementData[lastRet = i];' which doesn't do the needful) to Integer. So the Exception.

Thanks,
 
Consider Paul's rocket mass heater.
reply
    Bookmark Topic Watch Topic
  • New Topic