题目
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.
分析
题目要求返回链表的深度拷贝,意在要求得到的新链表中的随机指针指向关系要与原链表中一致。因此,该题的关键在于,如何记录原链表中random pointer的指向关系,并在新链表中体现。
代码
1.常规思路:利用map存储原链表node和新链表node的对应关系
/**
* 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) return NULL;
map<RandomListNode*, RandomListNode*> source_2_copy; //记录node对应关系
source_2_copy.insert(make_pair((RandomListNode*)NULL,(RandomListNode*)NULL)); //random pointer为NULL
RandomListNode *copy_head=new RandomListNode(head->label);
source_2_copy.insert(make_pair(head,copy_head));
RandomListNode *p_copy=copy_head;
RandomListNode *p_source=head->next;
//链表复制
while(p_source){
p_copy->next=new RandomListNode(p_source->label);
source_2_copy.insert(make_pair(p_source,p_copy->next));
p_copy=p_copy->next;
p_source=p_source->next;
}
p_source=head;
p_copy=copy_head;
//random pointer复制
while(p_source){
p_copy->random=(source_2_copy.find(p_source->random))->second;
p_source=p_source->next;
p_copy=p_copy->next;
}
return copy_head;
}
};
2.Bright Way:在原链表上为每个node new一个副本,然后拆分原链表,同时修改random pointer。(此方法会破坏原链表)
/**
* 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) return NULL;
RandomListNode *p=head;
//copy node
while(p){
RandomListNode *copy=new RandomListNode(p->label);
copy->next=p->next;
copy->random=p->random;
p->next=copy;
p=p->next->next;
}
p=head->next;
//get new list
while(p){
if(p->next)
p->next=p->next->next;
if(p->random)
p->random=p->random->next;
p=p->next;
}
return head->next;
}
};