| Author |
Casting of class types
|
Oleg Korsakov
Greenhorn
Joined: Jan 14, 2007
Posts: 14
|
|
Hello! There is one competent book ( let me note that they recommend JavaRanch also - http://www.ii.uib.no/~khalid/pgjc2e/resources.html ) where I found small example: class Light { /* ... */ } class LightBulb extends Light { /* ... */ } class SpotLightBulb extends LightBulb { /* ... */ } class TubeLight extends Light { /* ... */ } class NeonLight extends TubeLight { /* ... */ } public class WhoAmI { public static void main(String[] args) { boolean result1, result2, result3, result4, result5; Light light1 = new LightBulb(); // (1) // String str = (String) light1; // (2) Compile time error. // result1 = light1 instanceof String; // (3) Compile time error. result2 = light1 instanceof TubeLight; // (4) false. Peer class. // TubeLight tubeLight1 = (TubeLight) light1; // (5) ClassCastException. result3 = light1 instanceof SpotLightBulb; // (6) false: Superclass // SpotLightBulb spotRef = (SpotLightBulb) light1;// (7) ClassCastException light1 = new NeonLight(); // (8) if (light1 instanceof TubeLight) { // (9) true TubeLight tubeLight2 = (TubeLight) light1; // (10) OK // Can now use tubeLight2 to access object of class NeonLight. } } } I thought that in lines (6)&(7) was true because light1 is the reference of the supertype Light and that it must be higher in the instanceof operator than type of the subtype SpotLightBulb (last one - lower - in the inheritance hierarchy). And the purpose of casting is to cast the supertype to the type of the subtype ( (<subtype> <supertypeRef> ), but line (7) is invalid. Why? And in the instanceof operator where must be <objectRef> in the inheritance hierarchy higher or lower than the target type ( <objectRef> instanceof <targetType> ) ? And vice versa in lines (8),(9) I guess that here is executing the casting of the subtype to supertype and that this casting can be execute by using an assignment: tubelight2 = light1; Where are my thoughts wrong?
|
 |
Jeanne Boyarsky
internet detective
Marshal
Joined: May 26, 2003
Posts: 26192
|
|
light1 is a LightBulb class. This means it is also a Light (because you can go up the hierarchy.) However, it is not a SpotLightBulb because that is lower in the hierarchy. This is similar to "a dog is an animal, but not all dogs are poodles." The purpose of casting is to cast the supertype to the type of the subtype is to show that Java will give you an error. This is not something you want to do. <objectRef> instanceof <targetType> - either can be higher. If objectRef is higher, it will return false. If targetType is higher, it will return true.
|
[Blog] [JavaRanch FAQ] [How To Ask Questions The Smart Way] [Book Promos]
Blogging on Certs: SCEA Part 1, Part 2 & 3, Core Spring 3, OCAJP, OCPJP beta, TOGAF part 1 and part 2
|
 |
Oleg Korsakov
Greenhorn
Joined: Jan 14, 2007
Posts: 14
|
|
Thank you, Jeanne, for your answer but let me concretize a little to get real clarification ... So we have to cast LightBulb down to SpotLightBulb ( 'dog' to 'poodle' ) But it is not correct in that book. Is it correct really ? ( to cast to the type that is lower in the hierarhy ) And if objectRef is higher, it will return false ... then the downward direction of casting will be lost. I guess we have to check to true before casting whether we can cast downward <objectRef> to <targetType> that is lower (i mean <targetType> here is a poople and objectRef here refers to a dog so let me guess that 'dog instanceof poodle' gives 'true')
|
 |
Ernest Friedman-Hill
author and iconoclast
Marshal
Joined: Jul 08, 2003
Posts: 24057
|
|
A cast of a reference type never changes the actual object; it only changes the compiler's idea of what the reference points to. If an object was created with "new LightBulb()", then it is a LightBulb, but is not, and never can be, a SpotLightBulb. If, on the other hand, an object was created with "new SpotLightBulb()", then it is a SpotLightBulb, which is a kind of LightBulb, and you can have a variable of either of these types pointing to it. If you have a variable of type LightBulb pointing to a SpotLightBulb, and you want to tell the compiler that it's really a SpotLightBulb, then you can use a cast; but the cast doesn't change the object at all.
|
[Jess in Action][AskingGoodQuestions]
|
 |
Oleg Korsakov
Greenhorn
Joined: Jan 14, 2007
Posts: 14
|
|
|
My special thanks to Ernest too, especially in "A cast of a reference type never changes the actual object".
|
 |
 |
|
|
subject: Casting of class types
|
|
|