>深拷贝:深拷贝是指源对象与拷贝对象互相独立,其中任何一个对象的改动都不会对另外一个对象造成影响
解法一:
对于这个问题,我们可以分三部解决,
1、new出新节点,让新节点的next、data域等于老节点,然后将新节点老节点拼起来
ListNode cur=head;
//依次遍历链表实现连接
while(cur!=null) {
ListNode node=new ListNode(cur.data,cur.next,null);
//定义一个临时节点保存cur的next域,防止它与新节点相连后找不到以前的next域
ListNode temp=cur.next;
cur.next=node;
cur=temp;
2、处理它的random域
//cur遍历完链表走到末尾,此时我们将他拉回来
cur=head;
while(cur!=null) {
if(cur.random!=null) {
cur.next.random=cur.random.next;
cur=cur.next.next;
}else {
cur.next.random=null;
cur=cur.next.next;
}
}
3、将新旧链表分开
cur=head;
ListNode newHead=cur.next;
while(cur.next!=null) {
ListNode temp=cur.next;
cur.next=temp.next;
cur=temp;
}
return newHead;
/*
// Definition for a Node.
class Node {
public int val;
public Node next;
public Node random;
public Node() {}
public Node(int _val,Node _next,Node _random) {
val = _val;
next = _next;
random = _random;
}
};
*/
class Solution {
public Node copyRandomList(Node head) {
if(head==null) {
return null;
}
//将新老节点串成一个链表
Node cur=head;
while(cur!=null) {
Node node=new Node(cur.val,cur.next,null);
Node temp=cur.next;
cur.next=node;
cur=temp;
}
cur=head;
//处理random;
while(cur!=null) {
if(cur.random!=null) {
cur.next.random=cur.random.next;
}else {
cur.next.random=null;
}
cur=cur.next.next;
}
//拆分链表,cur>代表需要拆分的节点
cur=head;
Node newHead=cur.next;
while(cur.next!=null) {
Node temp=cur.next;
cur.next=temp.next;
cur=temp;
}
return newHead;
}
}``
解法二:Map法
public Node copyRandomList(Node head) {
if(head==null) {
return null;
}
Map<Node,Node> m=new HashMap<>();
Node node=head;
while(node!=null){//1. 遍历链表,将原节点作为key,拷贝节点作为value保存在map中
m.put(node,new Node(node.val));
node=node.next;
}
node=head;
while(node!=null) {//2、拷贝next域
m.get(node).next=m.get(node.next);
node=node.next;
}
node=head;
while(node!=null) {//拷贝random域
m.get(node).random=m.get(node.random);
node=node.next;
}
return m.get(head);
}