美文网首页
2018-05-28 对象clone()方法

2018-05-28 对象clone()方法

作者: MiaLing007 | 来源:发表于2018-05-28 17:47 被阅读0次

java 的基类Object中定义了clone()(克隆)方法,但该方法并不是每个类都能调用,虽然该方法在Object中定义为protected作用域。
Object中方法:

    protected native Object clone() throws CloneNotSupportedException;

想要使用clone()方法,必须Cloneable接口,且重写clone()方法。

例如:


class MyObject implements Cloneable {
    int i;
    MyObject(int ii) {i = ii;}
    protected Object clone() {
        Object o = null;
        try {
            o = super.clone();
        } catch (CloneNotSupportedException e) {
            System.out.println("MyObject can't clone");
        }
        return o;
    }
    public String toString() {
        return Integer.toString(i);
    }
}

public class LocalCopy {
    static MyObject g(MyObject v) {
        v.i++;
        return v;
    }
    static MyObject f(MyObject v) {
        v = (MyObject)v.clone();
        v.i++;
        return v;
    }
    public static void main(String[] args) {
        MyObject a = new MyObject(11);
        MyObject b = g(a);
        if (a == b)
            System.out.println("a == b");
        else
            System.out.println("a != b");
        System.out.println("a = " + a);
        System.out.println("b = " + b);
        
        MyObject c = new MyObject(47);
        MyObject d = f(c);
        if (c == d)
            System.out.println("c == d");
        else
            System.out.println("c != d");
        System.out.println("c = " + c);
        System.out.println("d = " + d);
    }
}

输出结果为:

a == b
a = 12
b = 12
c != d
c = 47
d = 48

在LocalCopy 中,两个方法g()和f()揭示出两种参数传递方法间的差异。其中,g()演示的是按引用传递,
它会修改外部对象,并返回对那个外部对象的一个引用。而f()是对自变量进行克隆,所以将其分离出来,
并让原来的对象保持独立。随后,它继续做它希望的事情。甚至能返回指向这个新对象的一个句柄,而且不
会对原来的对象产生任何副作用。注意下面这个多少有些古怪的语句:
v = (MyObject)v.clone();
它的作用正是创建一个本地副本。为避免被这样的一个语句搞混淆,记住这种相当奇怪的编码形式在Java 中
是完全允许的,因为有一个名字的所有东西实际都是一个句柄。所以句柄v 用于克隆一个它所指向的副本,
而且最终返回指向基础类型Object 的一个句柄(因为它在Object.clone()中是那样被定义的),随后必须
将其造型为正确的类型。

clone()该方法为浅克隆,浅层的复制

例如:

public class Snake implements Cloneable{
    private Snake next;
    private char c;
    
    Snake(int i, char x) {
        c = x;
        if (--i > 0)
            next = new Snake(i, (char)(x + 1));
    }
    void increment() {
        c++;
        if (next != null)
            next.increment();
    }
    public String toString() {
        String s = ":" + c;
        if (next != null)
            s +=next.toString();
        return s;
    }
    public Object clone() {
        Object o = null;
        try {
            o = super.clone();
        } catch (CloneNotSupportedException e) {
            e.printStackTrace();
        }
        return o;
    }
    public static void main(String args[]) {
        Snake s = new Snake(5, 'a');
        System.out.println("s = " + s);
        Snake s2 = (Snake)s.clone();
        System.out.println("s2 = " + s2);
        s.increment();
        System.out.println("after s.increment, s2 = " + s2);
    }
}

一条Snake(蛇)由数段构成,每一段的类型都是Snake。所以,这是一个一段段链接起来的列表。所有段都
是以循环方式创建的,每做好一段,都会使第一个构建器参数的值递减,直至最终为零。而为给每段赋予一
个独一无二的标记,第二个参数(一个Char)的值在每次循环构建器调用时都会递增。
increment()方法的作用是循环递增每个标记,使我们能看到发生的变化;而toString 则循环打印出每个标
记。输出如下:

s = :a:b:c:d:e
s2 = :a:b:c:d:e
after s.increment, s2 = :a:c:d:e:f

这意味着只有第一段才是由Object.clone()复制的,所以此时进行的是一种“浅层复制”。若希望复制整条
蛇——即进行“深层复制”——必须在被覆盖的clone()里采取附加的操作。
通常可在从一个能克隆的类里调用super.clone(),以确保所有基础类行动(包括Object.clone())能够进
行。随着是为对象内每个句柄都明确调用一个clone();否则那些句柄会别名变成原始对象的句柄。构建器
的调用也大致相同——首先构造基础类,然后是下一个衍生的构建器⋯⋯以此类推,直到位于最深层的衍生
构建器。区别在于clone()并不是个构建器,所以没有办法实现自动克隆。为了克隆,必须由自己明确进
行。

相关文章

  • 2018-05-28 对象clone()方法

    java 的基类Object中定义了clone()(克隆)方法,但该方法并不是每个类都能调用,虽然该方法在Obje...

  • 面试:Object 方法与原理

    Object 方法与原理 1. clone 方法 clone 方法的用法是对象的浅拷贝和深拷贝,clone是浅拷贝...

  • Java 集合深度复制

    泛型对象实现 Cloneable 接口 重写泛型对象的 clone 方法 使用的时候调用 泛型对象的 clone...

  • 第11条:谨慎地覆盖clone

    clone 方法使用详解 clone顾名思义就是复制, 在Java语言中, clone方法被对象调用,所以会复制对...

  • Clone() method in Java

    原文:geeks4geeks Java 中的 clone() 方法 对象 clone 是指创建对象的精确拷贝,它创...

  • java中clone方法的实现

    java中仅有的创建对象的两种方式:①.使用new操作符创建对象;②.使用clone方法复制对象。由于clone方...

  • 详解Java中的clone方法 -- 深拷贝和浅拷贝

    Java中对象的创建 clone顾名思义就是复制, 在Java语言中, clone方法被对象调用,所以会复制对象。...

  • Java基础-Object类

    Object是Java所有类的父类,其重要方法包括: 一、clone() clone()方法创建并返回该对象的一个...

  • 【Java】对Object.clone的理解

    Object.clone的理解 通过实现Cloneable接口和重写clone方法可以实现拷贝对象。 这里clon...

  • 浅拷贝和深拷贝

    clone方法 clone是定义一个Object类下基本方法之一: 使用的时候需要继承object对象,并且为了可...

网友评论

      本文标题:2018-05-28 对象clone()方法

      本文链接:https://www.haomeiwen.com/subject/qjngjftx.html