138. Copy List with Random Pointer

Difficulty:
Related Topics:
Similar Questions:

Problem

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.

Solution (Java)

/*
// Definition for a Node.
class Node {
    int val;
    Node next;
    Node random;

    public Node(int val) {
        this.val = val;
        this.next = null;
        this.random = null;
    }
}
*/

class Solution {
    public Node copyRandomList(Node head) {
        if (head == null) {
            return null;
        }
        // first pass to have a clone node point to the next node. ie A->B becomes A->clonedNode->B
        Node curr = head;
        while (curr != null) {
            Node clonedNode = new Node(curr.val);
            clonedNode.next = curr.next;
            curr.next = clonedNode;
            curr = clonedNode.next;
        }
        curr = head;
        // second pass to make the cloned node's random pointer point to the orginal node's randome
        // pointer.
        // ie. A's random pointer becomes ClonedNode's random pointer
        while (curr != null) {
            if (curr.random != null) {
                curr.next.random = curr.random.next;
            } else {
                curr.next.random = null;
            }
            curr = curr.next.next;
        }
        curr = head;
        // third pass to restore the links and return the head of the cloned nodes' list.
        Node newHead = null;
        while (curr != null) {
            Node clonedNode;
            if (newHead == null) {
                clonedNode = curr.next;
                newHead = clonedNode;
            } else {
                clonedNode = curr.next;
            }
            curr.next = clonedNode.next;
            if (curr.next != null) {
                clonedNode.next = curr.next.next;
            } else {
                clonedNode.next = null;
            }
            curr = curr.next;
        }
        return newHead;
    }
}

Solution (Javascript)

/**
 * // Definition for a Node.
 * function Node(val, next, random) {
 *    this.val = val;
 *    this.next = next;
 *    this.random = random;
 * };
 */

/**
 * @param {Node} head
 * @return {Node}
 */
var copyRandomList = function(head) {
    let pmap = new Map(), dummy = {}, curr = head, copy = dummy;
    while (curr) {
        let newNode = new Node(curr.val, null, null);
        pmap.set(curr, newNode);
        copy.next = newNode, copy = newNode, curr = curr.next;
    }
    curr = head, copy = dummy.next;
    while (curr) {
        copy.random = pmap.get(curr.random);
        curr = curr.next, copy = copy.next;
    }
    return dummy.next;
};

Explain:

ES6Map 可以用任意类型的 key。如果用 labelkey 的话,可能重复,直接 objectkey 就好。

Complexity: