2

Java 文档说 -

Object 类本身并没有实现接口 Cloneable,因此在类为 Object 的对象上调用 clone 方法将导致在运行时抛出异常。

这就是为什么 Object 类中的 clone 方法受到保护的原因?是这样吗 ?

这意味着任何不实现可克隆的类在调用其克隆方法时都会抛出 CloneNotSupported 异常。

我运行了一个测试程序

public class Test extends ABC implements Cloneable{

    @Override
    public Object clone() throws CloneNotSupportedException {
        System.out.println("calling super.clone");
            return super.clone();
    }

    public static void main(String[] args) {
        Test t = new Test();
        try{
        t.clone();
        }
        catch (Exception e) {
            e.printStackTrace();
        }
    }
}
class ABC{

}

从 Class Test 的克隆方法 super.clone 被调用?

为什么它不抛出异常?

4

6 回答 6

2

Test实例的继承树t看起来像

Object
  ABC
    Test

Test也实现Cloneable了,这意味着当您调用 methodsuper.clone() Objectclone方法时将被调用。它检查实例是否t实现了Cloneable接口。由于它确实实现了该方法,因此不会引发异常。

于 2010-08-13T07:39:07.187 回答
1

我会说一个很好的问题来迷惑受访者:)。

至于它不抛出异常的原因。以对象的方式思考它。您的 t 对象属于实现可克隆的 Test 类。当您调用方法 super.clone 时,它​​仍然是 Test 类的对象,因此没有理由抛出 CloneNotSupported 异常。如果它是类 Object 本身的对象,它就会抛出异常。

于 2010-08-13T13:02:03.030 回答
1

为什么 Object 类中有 clone 方法protected

这样选择支持克隆的类就不会被迫在其公共 API 中公开它。

如您的示例所示,允许子类覆盖具有比方法的继承版本更多访问权限的方法。您不能以这种方式减少方法的访问。

这意味着任何不实现可克隆的类在调用其克隆方法时都会抛出 CloneNotSupported 异常。

那是对的。

从 Class Test 的克隆方法 super.clone 被调用?

那是对的。

为什么它不抛出异常?

因为你已经声明你的类实现了Cloneable. 如果你没有这样做,它抛出一个异常......假设你的克隆方法仍然被调用super.clone()

于 2010-08-13T07:43:35.633 回答
1

Cloneable 接口是一个标记接口,表示实现类支持克隆方法。super.clone() 不抛出异常的原因是它被调用的基础对象是可通过继承克隆的。

来自 Javadoc:

一个类实现了 Cloneable 接口,以向 Object.clone() 方法指示该方法可以合法地对该类的实例进行逐个字段的复制。

在未实现 Cloneable 接口的实例上调用 Object 的 clone 方法会导致抛出异常 CloneNotSupportedException。

请参阅:可克隆(Java 平台 SE 6)

于 2010-08-13T07:38:53.943 回答
1

因为你的类实现了Cloneable. 来自的JavadocCloneable

一个类实现了 Cloneable 接口,以向 Object.clone() 方法指示该方法可以合法地对该类的实例进行逐个字段的复制。

所以这允许使用Object'clone()方法。它(再次根据 Javadoc)只是一个覆盖的约定clone()。如果您不覆盖它并且Object'sclone()方法执行逐个字段的复制,CloneNotSupportedException则如果其中一个字段本身不可克隆,您可能仍会得到一个。因此,最好的建议是覆盖它。

于 2010-08-13T07:39:17.140 回答
1

这可能会给你答案为什么方法受保护 为什么克隆方法受保护

它不会抛出异常,因为您实现了 Cloneable。从可克隆文档中:

“一个类实现了 Cloneable 接口以向 Object.clone() 方法指示该方法对该类的实例进行逐个字段的复制是合法的。在未实现的实例上调用 Object 的 clone 方法Cloneable 接口导致抛出异常 CloneNotSupportedException。"

但是当你实现它时,你告诉 Object 实现,制作一个字段到字段的副本是合法的,所以它不会抛出异常。

于 2010-08-13T07:51:41.917 回答