首先是您的简单问题:为什么要super.clone()
转换为MyClass
?那是因为声明HerClass.clone()
指定了一个返回值HerClass
,所以你必须将它转换为正确的类型。
现在,对于更困难的问题:如何super.clone()
实际返回MyClass
? 实际上我很难找到答案,但我确实在 Joshua Bloch 的 Effective Java 中找到了答案。Object.clone()
在我不太明白的背景中仍然有一些“魔法” 。
书中第11条:
实际上,程序员假设如果他们扩展一个类并从子类调用 super.clone,则返回的对象将是子类的一个实例。超类可以提供此功能的唯一方法是返回通过调用 super.clone 获得的对象。如果一个克隆方法返回一个由构造函数创建的对象,那么它将具有错误的类。因此,如果您在非最终类中重写 clone 方法,您应该返回一个通过调用 super.clone 获得的对象。如果一个类的所有超类都遵守这个规则,那么调用 super.clone 最终会调用 Object 的 clone 方法,创建一个正确类的实例。
我最初试图通过编写程序来回答您的问题,但并不知道您总是必须调用super.clone()
. 我自制的克隆方法是返回一个从构造函数()生成HerClass
的新实例。代码已编译,但在我尝试强制转换时执行失败。只有被链接的方法才能返回一个值,该值是其子类型之一的实例。HerClass
new HerClass()
(MyClass) super.clone()
Object.clone()
请注意,如果HerClass.clone()
没有显式实现,默认情况下它只是返回Object.clone()
. 默认方法具有protected
访问权限,但由于您是从子类调用它,所以这不是问题。