# LeetCode – 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.

Java Solution 1

We can solve this problem by doing the following steps:

1. copy every node, i.e., duplicate every node, and insert it to the list
2. copy random pointers for all newly created nodes
3. break the list to two
```public RandomListNode copyRandomList(RandomListNode head) {   if (head == null) return null;   RandomListNode p = head;   // copy every node and insert to list while (p != null) { RandomListNode copy = new RandomListNode(p.label); copy.next = p.next; p.next = copy; p = copy.next; }   // copy random pointer for each new node p = head; while (p != null) { if (p.random != null) p.next.random = p.random.next; p = p.next.next; }   // break list to two p = head; RandomListNode newHead = head.next; while (p != null) { RandomListNode temp = p.next; p.next = temp.next; if (temp.next != null) temp.next = temp.next.next; p = p.next; }   return newHead; }```

The break list part above move pointer 2 steps each time, you can also move one at a time which is simpler, like the following:

```while(p != null && p.next != null){ RandomListNode temp = p.next; p.next = temp.next; p = temp; }```

Java Solution 2 - Using HashMap

From Xiaomeng's comment below, we can use a HashMap which makes it simpler.

```public RandomListNode copyRandomList(RandomListNode head) { if (head == null) return null; HashMap<RandomListNode, RandomListNode> map = new HashMap<RandomListNode, RandomListNode>(); RandomListNode newHead = new RandomListNode(head.label);   RandomListNode p = head; RandomListNode q = newHead; map.put(head, newHead);   p = p.next; while (p != null) { RandomListNode temp = new RandomListNode(p.label); map.put(p, temp); q.next = temp; q = temp; p = p.next; }   p = head; q = newHead; while (p != null) { if (p.random != null) q.random = map.get(p.random); else q.random = null;   p = p.next; q = q.next; }   return newHead; }```
Category >> Algorithms
If you want someone to read your code, please put the code inside <pre><code> and </code></pre> tags. For example:
```<pre><code>
String foo = "bar";
</code></pre>
```
• Milan

same as copying a list without random pointer, but before creating a new node check for presence in alreadyCreated map.
``` public RandomListNode copyRandomList(RandomListNode head) { RandomListNode dummy = new RandomListNode(0); RandomListNode prev = dummy; // Map alreadyCreated = new HashMap(); while(head != null){ RandomListNode newNode = alreadyCreated.containsKey(head) ? alreadyCreated.get(head) : new RandomListNode(head.label); alreadyCreated.put(head,newNode); newNode.random = head.random == null || alreadyCreated.containsKey(head.random) ? alreadyCreated.get(head.random) : new RandomListNode(head.random.label); alreadyCreated.put(head.random,newNode.random); prev.next = newNode; prev = newNode; head = head.next; } return dummy.next; } ```

• Ranjith Sompalli

This is my solution

{
Map nodesMap = new HashMap();

return null;

{
}

for(RandomListNode originalNode : nodesMap.keySet())
{
nodesMap.get(originalNode).next = nodesMap.get(originalNode.next);
nodesMap.get(originalNode).random = nodesMap.get(originalNode.random);
}
return nodesMap.get(first);
}

• Roderick Gao

This is my solution: keep putting .random and next into HashMap, then we just need one iteration instead of two.

• traceformula

I also have the sames solutions. And I added another solution using recursion:
( url: http://traceformula.blogspot.com/2015/07/copy-list-with-random-pointers.html )

public class Solution {

public HashMap createdNode;

createdNode = new HashMap();

}
private RandomListNode cc(RandomListNode node) {

if(node == null)

{

return null;

}

RandomListNode newNode = new RandomListNode(node.label);
createdNode.put(node, newNode);

newNode.next = cc(node.next);

//now assign the random pointer

RandomListNode newRandom = null;

if(node.random != null)

{

newRandom = createdNode.get(node.random);

}

newNode.random = newRandom;

return newNode;

}

}

• nuurtila

This does not create a copy. Both p and q are references to the same list.

• Monica Shankar

can’t we simply do this

while(p.random!=null)
{
q.label=p.label;
q.random=p.random;
q=q.random;
p=p.random;
}

I really don’t see the point of having random and next as complementary fields for linkedlist. Correct me if I am wrong.

• Alyssa Chen

p.random is the node is the original list. Since newly added nodes are always the next to original nodes, so p.next.random = p.random.next;

• Cracker
• Parag Chaudhari

This solution doesnot work if list has duplicate elements.

• Wilson Ziyou Zheng

shouldn’t it be: p.next.random = p.random;

• zhou2214

good solutions

• Kartrace

That’s very nice solutions! The first might be very hard to think of if one were in the interview, it’s a little bit tricky, the second one is reasonable but with the cost of additional memory.

• ryanlr

Okay, I see.

• I just put my code in <pre> <code>, and Disqus changed them, I don’t know why 🙁 Maybe the “>” confused Disquz.

For first line, it should be HashMap < randomlistnode, randomlistnodepre > n2nMap = new HashMap < randomlistnode, randomlistnodepre >.

And for the second line, it should be not existed.

• ryanlr

Good solution. Is this line legal?

``` HashMap n2nMap = new HashMap(); ```

• xmpy

What about using hash map to store the original node reference to new node reference mapping?
My implementation is:
(1) first foreach node in list, copy it, store the original node to new node mapping in hashmap

(2)Still foreach node in original list, if its random attribute is not null, change the corresponding new node’s random attribute based on the hashmap.

Here is my code:
``` public RandomListNode copyRandomList(RandomListNode head) { if(head ==null) return null; HashMap n2nMap = new HashMap(); RandomListNode newHead = new RandomListNode(head.label); RandomListNode p = head; RandomListNode q = newHead; n2nMap.put(head, newHead); p = p.next; while(p != null){ RandomListNode temp = new RandomListNode(p.label); n2nMap.put(p,temp); q.next = temp; q = temp; p = p.next; } p = head; q = newHead; while(p!=null){ if(p.random != null) q.random = n2nMap.get(p.random); else q.random = null; p = p.next; q = q.next; } return newHead; } ```