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. Listed two methods. One is using HashMap, one is copy without extra memory space.Pointer operation needs special attention.... Need to pay attention that these methods don't support multi-threads.
Return a deep copy of the list. Listed two methods. One is using HashMap, one is copy without extra memory space.Pointer operation needs special attention.... Need to pay attention that these methods don't support multi-threads.
#include <vector>
#include <iostream>
#include <unordered_map>
using namespace std;
struct RandomListNode {
int label;
RandomListNode* next, *random;
RandomListNode(int x) : label(x), next(NULL), random(NULL) {}
};
RandomListNode* setUpList() {
RandomListNode* head = NULL;
int number_1 = 1;
RandomListNode* tmp = new RandomListNode(number_1);
tmp->next = head;
head = tmp;
int number_2 = 2;
RandomListNode* tmp_second = new RandomListNode(number_2);
tmp_second->next = head;
head = tmp_second;
return head;
}
void setUpRandom(RandomListNode* head) {
RandomListNode* tmp = head;
while(tmp) {
RandomListNode* next = tmp->next;
tmp->random = next;
tmp = tmp->next;
}
}
void printValue(RandomListNode* head) {
RandomListNode* tmp = head;
while(tmp) {
cout << "the node is: " << tmp->label;
if(tmp->random) {
cout << " randome value is: " << tmp->random->label;
cout << endl;
}
cout << endl;
tmp = tmp->next;
}
<pre name="code" class="cpp">}
// Make deep copy with extra O(n) memory.
RandomListNode* copyRandomList(RandomListNode* head) {
if(!head) return NULL;
RandomListNode* dummy = new RandomListNode(-1); // make a dummy node as the duplicate head.
RandomListNode* curr = dummy;
unordered_map<RandomListNode*, RandomListNode*> oldToNew;
RandomListNode* tmp = head;
while(tmp) {
RandomListNode* newNode = new RandomListNode(tmp->label);
oldToNew[tmp] = newNode;
curr->next = newNode;
curr = curr->next;
tmp = tmp->next;
}
tmp = head;
while(tmp) {
if(tmp->random) {
oldToNew[tmp]->random = oldToNew[tmp->random];
}
tmp = tmp->next;
}
return dummy->next;
}
// NULL
// |
// 2->2'->1->1'->NULL
// | |
// ------>
void copyNext(RandomListNode* head) {
RandomListNode* tmp = head;
while(tmp) {
RandomListNode* next = tmp->next;
RandomListNode* newNode = new RandomListNode(tmp->label);
newNode->random = NULL;
tmp->next = newNode;
newNode->next = next;
tmp = next;
}
}
// ------>
// | |
// 2->2'->1->1'->NULL
// | |
// ------>
void copyRandom(RandomListNode* head) {
RandomListNode* tmp = head;
while(tmp) {
if(tmp->random) {
tmp->next->random = tmp->random->next;
}
tmp = tmp->next->next;
}
}
// 2->1->NULL
// | |
// -->
//
// 2'->1'->NULL
// | |
// --->
RandomListNode* splitListNodes(RandomListNode* head) {
RandomListNode* newHead = head->next;
while(head) {
RandomListNode* tmp = head->next;
head->next = tmp->next;
head = head->next;
if(tmp->next) {
tmp->next = tmp->next->next;
}
}
return newHead;
}
// make deep copy without using extra memory.
RandomListNode* copyRandomListII(RandomListNode* head) {
copyNext(head);
copyRandom(head);
return splitListNodes(head);
}
// NULL
// |
// The listNode is setUp as 2->1->NULL.
// | |
// ->
// ->
int main(void) {
RandomListNode* head = setUpList();
setUpRandom(head);
printValue(head);
cout << endl;
cout << "make a copy" << endl;
cout << endl;
RandomListNode* dup = copyRandomListII(head);
printValue(dup);
}