138. Copy List with Random Pointer

A linked list is given such that each node contains an additional random pointer which could point to any node in the list or null.

Return a deep copy of the list.

 

Before this problem: the difference between shallow and deep copy! https://www.geeksforgeeks.org/deep-shallow-lazy-copy-java-examples/ 

Soluton 1: use hasmap (key: old list, value: new list) copy val first and then the next and random pointer.

time: O(n) two while loops 

space: O(n) because of hashmap

/**
 * Definition for singly-linked list with a random pointer.
 * class RandomListNode {
 *     int label;
 *     RandomListNode next, random;
 *     RandomListNode(int x) { this.label = x; }
 * };
 */
public class Solution {
    public RandomListNode copyRandomList(RandomListNode  head) {
        //shallow
        //RandomListNode temp = head;
        //deep copy
        Map<RandomListNode, RandomListNode> map = new HashMap<>();//key: old list, value: new list
        //copy the value first
        RandomListNode cur = head;
        while(cur != null){
            map.put(cur, new RandomListNode(cur.label));    
            cur = cur.next;
        }
        //copy next and random
        cur = head;
        while(cur != null){
            map.get(cur).next = map.get(cur.next);
            map.get(cur).random = map.get(cur.random);
            cur = cur.next;
        }
        return map.get(head);
    }
}

 

Solution 2: three loops with O(1) space

/**
 * Definition for singly-linked list with a random pointer.
 * class RandomListNode {
 *     int label;
 *     RandomListNode next, random;
 *     RandomListNode(int x) { this.label = x; }
 * };
 */
public class Solution {
    public RandomListNode copyRandomList(RandomListNode  head) {
        if(head == null) return head;
        //three loops 
        //1. add new node after old node
        RandomListNode cur = head;
        while(cur!= null){
            RandomListNode newNode  = new RandomListNode(cur.label);
            newNode.next = cur.next;
            cur.next = newNode;
            cur = newNode.next;
        }
        
        //2. assign the random pointer, 1 1 2 2 3 3 (old new)
        cur = head;
        while(cur != null){
            if(cur.random!= null)//for last new node 
                cur.next.random = cur.random.next; // assign old node's random to newnode's random
            cur = cur.next.next;
        }
        //3. detatch the two lists and keep old list
        RandomListNode newHead = head.next;
        RandomListNode node = head;
        while(node!=null){
            RandomListNode newNode = node.next;//new list 
            node.next = newNode.next; // old list//node.next = node.next.next
            if(newNode.next!=null)
            newNode.next = newNode.next.next ; // new list, 
            
            node = node.next; //old list
        }
        
        return newHead;
    }
}

Reference1 https://blog.csdn.net/linhuanmars/article/details/22463599

Reference 2:https://blog.csdn.net/liuchonge/article/details/74858192

posted @ 2018-08-07 06:09  wz30  阅读(175)  评论(0编辑  收藏  举报