力扣刷题-热题100题-第32题(c++、python)
138. 随机链表的复制 - 力扣(LeetCode)https://leetcode.cn/problems/copy-list-with-random-pointer/?envType=study-plan-v2&envId=top-100-liked
回溯哈希
c++利用unordered_set,python利用字典,创造哈希表来记录遍历过的随机链表,键作为原链表,值作为新链表。
遍历随机链表时,对于未遍历过的节点(不在哈希表中)创建新的节点并写入哈希表,然后调用自己创建next与random,若已遍历过(在哈希表内),就返回哈希表的值。
//c++
/*
// Definition for a Node.
class Node {
public:
int val;
Node* next;
Node* random;
Node(int _val) {
val = _val;
next = NULL;
random = NULL;
}
};
*/
class Solution
{
private: std::unordered_map<Node*,Node*> v;
public:
Node* copyRandomList(Node* head)
{
if(head==nullptr) return nullptr;
if(v.find(head)==v.end())
{
Node* a=new Node(head->val);
v[head]=a;
a->next=copyRandomList(head->next);
a->random=copyRandomList(head->random);
return a;
}
else return v[head];
}
};
#python
"""
# Definition for a Node.
class Node:
def __init__(self, x: int, next: 'Node' = None, random: 'Node' = None):
self.val = int(x)
self.next = next
self.random = random
"""
a={}
class Solution:
def copyRandomList(self, head: 'Optional[Node]') -> 'Optional[Node]':
if head==None:
return None
if head not in a:
b=Node(head.val)
a[head]=b
b.next=self.copyRandomList(head.next)
b.random=self.copyRandomList(head.random)
return a[head]
迭代节点拆分
就是在原链表的每个元素后照葫芦画瓢创建一个新元素类比复制原元素的各个指向。
第一层循环创建元素并间隔插入原链表复制next
第二层循环将新元素的random指向原元素的random后的next
第三层循环将新元素从中拆下来得到新链表
//c++
/*
// Definition for a Node.
class Node {
public:
int val;
Node* next;
Node* random;
Node(int _val) {
val = _val;
next = NULL;
random = NULL;
}
};
*/
class Solution
{
public:
Node* copyRandomList(Node* head)
{
if(head==nullptr) return nullptr;
for(Node* i=head;i!=nullptr;i=i->next->next)
{
Node* a=new Node(i->val);
a->next=i->next;
i->next=a;
}
for(Node* i=head;i!=nullptr;i=i->next->next)
{
Node* a=i->next;
a->random=(i->random==nullptr)?nullptr:i->random->next;
}
Node* ans=head->next;
for(Node* i=head;i!=nullptr;i=i->next)
{
Node* a=i->next;
i->next=i->next->next;
a->next=(a->next==nullptr)?nullptr:a->next->next;
}
return ans;
}
};
#python
"""
# Definition for a Node.
class Node:
def __init__(self, x: int, next: 'Node' = None, random: 'Node' = None):
self.val = int(x)
self.next = next
self.random = random
"""
class Solution:
def copyRandomList(self, head: 'Optional[Node]') -> 'Optional[Node]':
if head==None:
return None
i=head
while i:
a=Node(i.val)
a.next=i.next
i.next=a
i=i.next.next
i=head
while i:
a=i.next
a.random=i.random.next if i.random else None
i=i.next.next
ans=head.next
i=head
while i:
a=i.next
i.next=i.next.next
a.next=a.next.next if a.next else None
i=i.next
return ans