java - 有效的Java。可克隆界面

标签 java cloneable effective-java

我阅读了《Effective Java》一书,但不理解解释可克隆接口(interface)的一段。谁能给我解释一下这一段:

...programmers assume that if they extend a class and invoke super.clone from the subclass, the returned object will be an instance of the subclass. The only way a superclass can provide this functionality is to return an object obtained by calling super.clone. If a clone method returns an object created by a constructor, it will have the wrong class.

谢谢。

最佳答案

首先我要注意 clone 本身是坏的,而像 Sheep(Sheep cloneMe) 这样的复制构造函数是一个更优雅的习惯用法比clone,考虑到Cloneable合约非常弱。您可能已经知道这一点,因为您正在阅读这本书,但值得将其放在这里。

无论如何,回答这个问题:

Object.clone() 将创建一个与调用它的对象类型相同的对象。出于这个原因,强烈建议“级联”到 Object 以获得您计划返回的结果。如果有人决定不遵循这个约定,你最终会得到一个违反约定的类类型的对象,这会导致很多问题。

为了说明我有这样一个类

class Sheep implements Cloneable {

    Sheep(String name)...

    public Object clone() {
        return new Sheep(this.name); // bad, doesn't cascade up to Object
    }
}

class WoolySheep extends Sheep {

    public Object clone() {
        return super.clone();
    }
}

突然间,如果我这样做

WoolySheep dolly = new WoolySheep("Dolly");
WoolySheep clone = (WoolySheep)(dolly.clone()); // error

我会得到一个异常,因为我从 dolly.clone() 返回的是一个 Sheep,而不是一个 WoolySheep

关于java - 有效的Java。可克隆界面,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11654176/

相关文章:

java - 我怎样才能减少这个长长的 if 语句列表?

java - 为什么 protected clone()方法无法使用同一包中的继承来访问

java - 为什么在泛型方法的定义中有时会省略返回类型之前的尖括号

java - 无法在 Spring Web 应用程序中打开属性文件

java - 我们可以在全局状态存储恢复期间调用处理器吗?

jquery - 在 jQuery 中克隆表单并增加索引

java - 在 LinkedList 上实现克隆

java - Effective Java教科书中的哈希码示例需要解释

java - 为 future 可能的可扩展性保留一个非最终值类

java - 多次查询一个巨大的集合。有没有更高效的解决方案?