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.

分析


本题实际上就是有向图的深拷贝。

方法一

时间复杂度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];
    }
};




posted @ 2017-02-19 22:03  copperface  阅读(310)  评论(0编辑  收藏  举报