解题思路
思路:
本来的想法是遍历两遍原链表,第一次复制next指针和val值,第二次复制random指针。
但是链表只能顺序遍历…无法直接让random指针指向哪个结点。
遂看题解(感恩!),了解到重点是实现链表1(原链表)和链表2(复制链表)之间的映射关系,即取到链表1结点时,能立刻取到对应的链表2上的结点。
大部分题解给了两种方法,思路一样实现手段不同。
一、 用HashMap实现 map.get(链表1结点n)=链表2对应结点n.
1.遍历链表1,创建链表2结点连接并一起放入HashMap;
2.再遍历链表1,复制random指针。
二、 将两链表交叉排列,实现 链表1结点1.next=链表2结点1; 链表2结点1.next=链表1结点2.
1.遍历链表1,并将循环中每个链1结点的next指针指向链表2对应结点。【实现链1结点3.next=链2结点3】
2.遍历链表12交叉结合体,设置random指针。【链1结点1.next.random=链1结点1.random.next】
3.遍历链表12交叉结合体,拆开next指针指向,分为两个链表。
这里只写方法一的代码。
代码【HashMap】:
class Node {
int val;
Node next;
Node random;
public Node(int val) {
this.val = val;
this.next = null;
this.random = null;
}
}
public Node copyRandomList(Node head) {
if(head==null)return null;//原链表为空则返回空
Node n1=head;
Map<Node,Node> map=new HashMap<>();
while(n1!=null){
Node n2=new Node(n1.val);/*原链表结点为n1,复制后的
链表结点n2,使n1和n2在Map中形成映射关系。*/
map.put(n1,n2);
n1=n1.next;
}
n1=head;
while(n1!=null){
map.get(n1).next=map.get(n1.next);
/*map.get(n1)=原链表结点n1对应的复制链表结点n2,即:
链表结点Node[val,random]
原链表: [1,2] - [2,1] - [3,1]
复制链表: [1,null] - [2,null] - [3,null]
当n1=[2,1]时,
map.get(n1)=[2,null](对应的n2)
*/
map.get(n1).random=map.get(n1.random);
n1=n1.next;
}
return map.get(head);
}