Java 自定义链表的深度克隆

Java 自定义链表的深度克隆,java,linked-list,clone,Java,Linked List,Clone,我正在尝试实现clone方法来对自定义链表(矩形对象)进行深度克隆。当列表中没有元素或只有一个元素时,我能够得到正确的值,但当列表中有多个元素时,我就不能得到正确的值。我认为问题在于MyLinkNode类中的克隆方法。有人能帮我做这个吗 注意:为了便于阅读,我缩短了代码 class Rectangle implements Cloneable { private double width; private double height; // setters and get

我正在尝试实现clone方法来对自定义链表(矩形对象)进行深度克隆。当列表中没有元素或只有一个元素时,我能够得到正确的值,但当列表中有多个元素时,我就不能得到正确的值。我认为问题在于MyLinkNode类中的克隆方法。有人能帮我做这个吗

注意:为了便于阅读,我缩短了代码

class Rectangle implements Cloneable {
    private double width;
    private double height;
    // setters and getters for these class variables

    public Object clone() {
        try {
            Object rectClone = super.clone();
            return (Rectangle) rectClone;
        } catch (CloneNotSupportedException c) {
            return null;
        }
    }
}


public class MyList implements Cloneable {
    private MyListNode head;

    public Object clone() {
        try {
            Object listClone = super.clone();
            if (head != null) {
                ((MyList) listClone).head = (MyListNode) head.clone();
            }
            return (MyList) listClone;
        } catch (CloneNotSupportedException c) {
            return null;
        }
    }
}


class MyListNode implements Cloneable {
    private Rectangle rectangle;
    private MyListNode next;
    // getter setter for class properties

    protected MyListNode clone() {
        try {
            Object NodeClone = super.clone();
            ((MyListNode) NodeClone).rectangle = (Rectangle) rectangle.clone();
            MyListNode temp = this.next;
            while (temp != null) {
                ((MyListNode) NodeClone).rectangle = (Rectangle) rectangle
                        .clone();
                temp = temp.getNext();
                //edited later, posted by mistake
                //clone();
            }
            return (MyListNode) NodeClone;
        } catch (CloneNotSupportedException c) {
            return null;
        }
    }
}
---使用递归的我的克隆方法(另一次尝试)--

--虽然结果似乎是正确的(对以前方法的修正),但这一方法似乎在整个过程中起了两次作用--


非常感谢您的帮助!我对克隆和自定义链表都是新手,并且已经尝试了很长时间:(

你的迭代方法是错误的。你必须克隆每个节点,所以你必须在列表类中进行。如果你尝试在第一个节点上克隆它,当你尝试克隆其余的节点时,它们将递归地克隆其余的节点。因此,第一个节点将克隆一次、第二次两次、第三次三次,等等

我将尝试修复您的递归方法

    if( temp == null){ // <-- temp is null!! should be != null
        ((MyListNode) nodeClone).rectangle = (Employee)this.rectangle.clone(); <-- Employee ?!?!
        ((MyListNode) nodeClone).next = this.next.clone();
        temp = temp.getNext(); <-- This throws NPE as temp is null!! But it is useless anyway. Remove this line.
    }

如果(temp==null){/那么这是我的方法。我认为它工作正常,但有人能证实吗

Object nodeClone = super.clone();
        MyListNode temp = this.next;
        if(temp == null){
            ((MyListNode) nodeClone).rectangle = (Employee) this.rectangle.clone();
            return (MyListNode)nodeClone;
        }else{
            while(temp != null){
                ((MyListNode) nodeClone).rectangle = (Rectangle) this.rectangle.clone();
                ((MyListNode) nodeClone).next = this.next.clone();
                temp = temp.getNext();
                return (MyListNode) nodeClone;

类以大写开头,但不包括其他内容(变量、字段、方法)应该从小写开始。这里的代码。链接不会永远持续。答案在这里,链接文件只是为了帮助和探测它。谢谢@user270349:这确实有效!我也能够理解我做错的部分。这最终帮助我修复了我的代码。所以,现在迭代方法也起作用了。再次感谢:)我已经在下面发布了我的方法。如果可能的话,你能检查一下吗:)不管它是否有效。它在任何情况下都是错误的。我猜这是MyListNode.clone方法。如果是这样,它是递归的,因为你正在调用
this.next.clone()
这确实是同一种方法。因此,您的方法是迭代和递归的。您正在克隆第一个节点一次,第二个节点两次,等等。难道您看不到吗?如果您在一个不称为克隆的方法中使用该代码(因此不会重载克隆),则与您调用
this.next.clone()时一样正确;
它不是递归的,但如果是迭代的,最好将此代码放在
MyList
类中。除非是递归的,否则“告诉”第一个节点克隆自身和其余节点是没有意义的。
    if( temp == null){ // <-- temp is null!! should be != null
        ((MyListNode) nodeClone).rectangle = (Employee)this.rectangle.clone(); <-- Employee ?!?!
        ((MyListNode) nodeClone).next = this.next.clone();
        temp = temp.getNext(); <-- This throws NPE as temp is null!! But it is useless anyway. Remove this line.
    }
protected MyListNode clone() {
    try {
        Object nodeClone = super.clone();
        ((MyListNode) nodeClone).rectangle = (Rectangle) this.rectangle.clone();
        if (this.next != null) {
            ((MyListNode) nodeClone).next = this.next.clone();
        }
        return (MyListNode) nodeClone;
    } catch (CloneNotSupportedException c) {
        throw new RuntimeException(c); // <<- This is the best for impossible conditions so if they happen you notice
    }
}
Object nodeClone = super.clone();
        MyListNode temp = this.next;
        if(temp == null){
            ((MyListNode) nodeClone).rectangle = (Employee) this.rectangle.clone();
            return (MyListNode)nodeClone;
        }else{
            while(temp != null){
                ((MyListNode) nodeClone).rectangle = (Rectangle) this.rectangle.clone();
                ((MyListNode) nodeClone).next = this.next.clone();
                temp = temp.getNext();
                return (MyListNode) nodeClone;