138. Copy List with Random Pointer
- Total Accepted: 98004
- Total Submissions: 368319
- Difficulty: Medium
- Contributors: Admin
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.
Subscribe to see which companies asked this question.
分析
本题实际上就是有向图的深拷贝。
方法一
时间复杂度O(3N)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 | /** * Definition for singly-linked list with a random pointer. * struct RandomRandomListNode { * int label; * RandomRandomListNode *next, *random; * RandomRandomListNode(int x) : label(x), next(NULL), random(NULL) {} * }; */ class Solution { public : RandomListNode *copyRandomList(RandomListNode *head) { if (head == NULL) return NULL; RandomListNode* p = head; //copy every node and link to one's next position while (p != NULL){ RandomListNode* next = p->next; RandomListNode* newNode = new RandomListNode(p->label); p->next = newNode; newNode->next = next; p = next; } //every new node's random link to orignal link's next node p = head; while (p != NULL){ if (p->random != NULL)p->next->random = p->random->next; p = p->next->next; } //split the list RandomListNode dummy1(0), dummy2(0); RandomListNode* p1 = &dummy1, * p2 = &dummy2; p = head; while (p != NULL){ p1->next = p; p1 = p1->next; p2->next = p->next; p2 = p2->next; p = p->next->next; if (p == NULL){ p1->next = NULL; p2->next = NULL; } } head = dummy1.next; return dummy2.next; } }; |
方法二
使用map去做,建立 新旧节点的 key-value 对,然后拷贝连接关系即可
(用C++写会runtime error, Java就没问题,不懂)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | /** * Definition for singly-linked list with a random pointer. * struct RandomListNode { * int label; * RandomListNode *next, *random; * RandomListNode(int x) : label(x), next(NULL), random(NULL) {} * }; */ class Solution { public : RandomListNode *copyRandomList(RandomListNode *head) { if (head == NULL) return NULL; unordered_map<RandomListNode*, RandomListNode*> map; RandomListNode* p = head; while (p != NULL){ map.insert({p, new RandomListNode(p->label)}); p = p->next; } for (auto p: map){ RandomListNode *newNode = (p.second); newNode->next = map[p.first->next]; newNode->random = map[p.first->random]; } return map[head]; } }; |
方法三
使用迭代,原理和方法二一样
1 2 3 4 5 6 7 8 9 10 11 12 13 | class Solution { public : unordered_map<RandomListNode*, RandomListNode*>mp; RandomListNode *copyRandomList(RandomListNode *head) { if (!head) return NULL; if (mp[head]!=NULL) return mp[head]; mp[head] = new RandomListNode(head->label); mp[head] -> next = copyRandomList(head->next); mp[head] -> random = copyRandomList(head->random); return mp[head]; } }; |