Up casting and ClassCastException

Started by
2 comments, last by TheChubu 10 years, 11 months ago

Well, casting up and changing the object type is not possible in Java. So now I am kinda stuck.

I have a root class called GameObject. It contains a function that looks like this:


public GameObject getClone(float x, float y)
{
       GameObject go = new GameObject();
       //Clone the data here

       return go;
}

Then we have MovableObject which extends GameObject:


public MovableObject getClone(float x, float y)
{
       MovableObject mo = (MovableObject) super.getClone(x,y);
      //Clone the data here

       return mo;
} 

The cast operation will trigger ClassCastException.

Since a MovableObject have all the variables GameObject have + more, it would make sense to call the super class function first and then continue on the divided class function.

Are there any efficient ways to solve this?

Advertisement

Try this :


public class GameObject implements Cloneable {
  public GameObject getClone(float x, float y) {
    try {
      GameObject go = (GameObject)(super.clone());
      //Clone the data here
      return go;
    } catch (CloneNotSupportedException ex) {
      throw new RuntimeException(ex);
    }
  }
} 

P.S. I don't think that your clone method should receive any parameter. Try to keep the cohesion of the methods.

The problem is that you actually creates a GameObject instead of a MovableObject. After an object is create it's impossible to change its runtime type. Casting is just for using different static type for this object. That means by casting you can refer the same object with different references. For example you can refer a MovableObject with a GameObject reference. Or if you get a GameObject reference but you know it points to a MovableObject, with casting you can refer to it as a MovableObject. But you can't refer a actual GameObject with a MoveableObject reference because it's not a MovableObject.

That's why you can't call the object creation code of the parent class from the child class. However you can call the data copying code if you separate it like this:

GameObject class:


public GameObject getClone()
{
    GameObject go = new GameObject();
    copyData(go);
    return go;
}

protected void copyData(GameObject other)
{
    other.someBasicData = someBasicData;
}

MovableObject class:


public MovableObject getClone(float x, float y)
{
    MovableObject mo = new MovableObject(x, y);
    copyData(mo);
    return mo;
}

protected void copyData(MovableObject other)
{
    super.copyData((GameObject)other);
    other.somethingNew = somethingNew;
}

That's called downcasting btw. Because you cast an object of a higher hierarchy (GameObject) to a lower hierarchy (MovableObject) in your hierarchy tree.

"I AM ZE EMPRAH OPENGL 3.3 THE CORE, I DEMAND FROM THEE ZE SHADERZ AND MATRIXEZ"

My journals: dustArtemis ECS framework and Making a Terrain Generator

This topic is closed to new replies.

Advertisement