138. 随机链表的复制
138. 随机链表的复制
题目
A linked list of length n
is given such that each node contains an additional random pointer, which could point to any node in the list, or null
.
Construct a deep copy of the list. The deep copy should consist of exactly n
brand new nodes, where each new node has its value set to the value of its corresponding original node. Both the next
and random
pointer of the new nodes should point to new nodes in the copied list such that the pointers in the original list and copied list represent the same list state. None of the pointers in the new list should point to nodes in the original list.
For example, if there are two nodes X
and Y
in the original list, where X.random --> Y
, then for the corresponding two nodes x
and y
in the copied list, x.random --> y
.
Return the head of the copied linked list.
The linked list is represented in the input/output as a list of n
nodes. Each node is represented as a pair of [val, random_index]
where:
val
: an integer representingNode.val
random_index
: the index of the node (range from0
ton-1
) that therandom
pointer points to, ornull
if it does not point to any node.
Your code will only be given the head
of the original linked list.
Example 1:
Input: head = [[7,null],[13,0],[11,4],[10,2],[1,0]]
Output: [[7,null],[13,0],[11,4],[10,2],[1,0]]
Example 2:
Input: head = [[1,1],[2,1]]
Output: [[1,1],[2,1]]
Example 3:
Input: head = [[3,null],[3,0],[3,null]]
Output: [[3,null],[3,0],[3,null]]
Constraints:
0 <= n <= 1000
-10^4 <= Node.val <= 10^4
Node.random
isnull
or is pointing to some node in the linked list.
题目大意
给你一个长度为 n
的链表,每个节点包含一个额外增加的随机指针 random
,该指针可以指向链表中的任何节点或空节点。
构造这个链表的 深拷贝。 深拷贝应该正好由 n
个 全新 节点组成,其中每个新节点的值都设为其对应的原节点的值。新节点的 next
指针和 random
指针也都应指向复制链表中的新节点,并使原链表和复制链表中的这些指针能够表示相同的链表状态。复制链表中的指针都不应指向原链表中的节点 。
例如,如果原链表中有 X
和 Y
两个节点,其中 X.random --> Y
。那么在复制链表中对应的两个节点 x
和 y
,同样有 x.random --> y
。
返回复制链表的头节点。
用一个由 n
个节点组成的链表来表示输入/输出中的链表。每个节点用一个 [val, random_index]
表示:
val
:一个表示Node.val
的整数。random_index
:随机指针指向的节点索引(范围从0
到n-1
);如果不指向任何节点,则为null
。
你的代码 只 接受原链表的头节点 head
作为传入参数。
解题思路
对于数据结构复制,不管怎么变,你就记住最简单的方式: 一个哈希表 + 两次遍历 。
第一次遍历专门克隆节点,借助哈希表把原始节点和克隆节点的映射存储起来;第二次专门组装节点,照着原数据结构的样子,把克隆节点的指针组装起来。
题目如果让你克隆带随机指针的二叉树,或者克隆图,都是一样的,只不过是遍历的方式从 for 循环迭代遍历变成 traverse 递归函数遍历罢了。
另外,这道题和 第 133 题 克隆图 是一模一样的,因为链表加一个随机指针本质上就变成了一幅图。
代码
/**
* // Definition for a Node.
* function Node(val, next, random) {
* this.val = val;
* this.next = next;
* this.random = random;
* };
*/
/**
* @param {Node} head
* @return {Node}
*/
var copyRandomList = function (head) {
let clone = new Map();
for (let p = head; p !== null; p = p.next) {
if (!clone.has(p)) {
clone.set(p, new Node(p.val));
}
}
for (let p = head; p !== null; p = p.next) {
if (p.next !== null) {
clone.get(p).next = clone.get(p.next);
}
if (p.random !== null) {
clone.get(p).random = clone.get(p.random);
}
}
return clone.get(head);
};
相关题目
题号 | 标题 | 题解 | 标签 | 难度 | 力扣 |
---|---|---|---|---|---|
133 | 克隆图 | [✓] | 深度优先搜索 广度优先搜索 图 1+ | 🟠 | 🀄️ 🔗 |
1485 | 克隆含随机指针的二叉树 🔒 | 树 深度优先搜索 广度优先搜索 2+ | 🟠 | 🀄️ 🔗 | |
1490 | 克隆 N 叉树 🔒 | 树 深度优先搜索 广度优先搜索 1+ | 🟠 | 🀄️ 🔗 |