Java: super.clone() method and inheritance

前端 未结 5 1901
栀梦
栀梦 2020-12-13 21:22

I have a quick question regarding the clone() method in Java, used as super.clone() in regard to inheritance - where I call the clone()

5条回答
  •  轮回少年
    2020-12-13 21:34

    Although one answer is accepted, I do not think it fully answers the first part of the question (why downcasting in subclasses always works). Although I cannot really explain it, I think I can clear up some of the poster's confusion which was the same as mine. We have the following classes

    class A implements Cloneable 
    {
       @Override
       protected A clone() throws CloneNotSupportedException // could be public
       { 
          Object clone = super.clone();
          System.out.println("Class A: " + clone.getClass()); // will print 'C'
          return (A) clone;
       }
    }
    
    class B extends A
    {
       @Override
       protected B clone() throws CloneNotSupportedException
       { 
          A clone = super.clone();
          System.out.println("Class B: " + clone.getClass()); // will print 'C'
          return (B) clone;
       }
    }
    
    class C extends B
    {
       @Override
       protected C clone() throws CloneNotSupportedException
       { 
          B clone = super.clone();
          System.out.println("Class C: " + clone.getClass()); // will print 'C'
          return (C) clone;
       }
    }
    
    static main(char[] argv)
    {
       C c = new C();
       C cloned_c = c.clone();
    }
    

    The result of this is that

    Class A: C

    Class B: C

    Class C: C

    is printed on the command line. So, as a matter of fact, the clone()method of Object somehow can look down the call stack and see which type of object at the start of the chain invoked clone(), then, provided the calls bubble up so that Object#clone()is actually called, an object of that type is created. So this happens already in class C, which is strange, but it explains why the downcasts do not result in a ClassCastException. I've checked with the OpenJDK, and it appears this comes by some Java black magic implemented in native code.

提交回复
热议问题