12
12
13
13
这里的话就有两种思路,一种需要遍历两边链表,一种只需要遍历一遍。
14
14
15
+ > 2020.3.3 更新,leetcode 增加了样例,之前没有重复的数字所以 ` key ` 存的 ` val ` ,现在有了重复数字,将 ` key ` 修改为 ` Node ` 。此外 ` Node ` 的无参的构造函数也被去掉了,也需要修改。
16
+
15
17
# 解法一
16
18
17
19
首先利用 ` HashMap ` 来一个不用思考的代码。
@@ -25,27 +27,24 @@ public Node copyRandomList(Node head) {
25
27
if (head == null ) {
26
28
return null ;
27
29
}
28
- HashMap<Integer , Node > map = new HashMap<> ();
30
+ HashMap<Node , Node > map = new HashMap<> ();
29
31
Node h = head;
30
- // 生成所有节点
31
32
while (h != null ) {
32
- Node t = new Node ();
33
- t. val = h. val;
34
- map. put(t. val, t);
33
+ Node t = new Node (h. val);
34
+ map. put(h, t);
35
35
h = h. next;
36
36
}
37
37
h = head;
38
- // 更新 next 和 random
39
38
while (h != null ) {
40
39
if (h. next != null ) {
41
- map. get(h. val ). next = map. get(h. next. val );
40
+ map. get(h). next = map. get(h. next);
42
41
}
43
42
if (h. random != null ) {
44
- map. get(h. val ). random = map. get(h. random. val );
43
+ map. get(h). random = map. get(h. random);
45
44
}
46
45
h = h. next;
47
46
}
48
- return map. get(head. val );
47
+ return map. get(head);
49
48
}
50
49
```
51
50
@@ -80,26 +79,24 @@ public Node copyRandomList(Node head) {
80
79
if (head == null ) {
81
80
return null ;
82
81
}
83
- HashMap<Integer , Node > map = new HashMap<> ();
82
+ HashMap<Node , Node > map = new HashMap<> ();
84
83
Node h = head;
85
- Node cur = new Node (); // 空结点,dummy 节点,为了方便头结点计算
84
+ Node cur = new Node (- 1 ); // 空结点,dummy 节点,为了方便头结点计算
86
85
while (h != null ) {
87
86
// 判断当前节点是否已经产生过
88
- if (! map. containsKey(h. val)) {
89
- Node t = new Node ();
90
- t. val = h. val;
91
- map. put(t. val, t);
87
+ if (! map. containsKey(h)) {
88
+ Node t = new Node (h. val);
89
+ map. put(h, t);
92
90
}
93
91
// 得到当前节点去更新它的 random 指针
94
- Node next = map. get(h. val );
92
+ Node next = map. get(h);
95
93
if (h. random != null ) {
96
94
// 判断当前节点是否已经产生过
97
- if (! map. containsKey(h. random. val)) {
98
- next. random = new Node ();
99
- next. random. val = h. random. val;
100
- map. put(next. random. val, next. random);
95
+ if (! map. containsKey(h. random)) {
96
+ next. random = new Node (h. random. val);
97
+ map. put(h. random, next. random);
101
98
} else {
102
- next. random = map. get(h. random. val );
99
+ next. random = map. get(h. random);
103
100
}
104
101
105
102
}
@@ -108,7 +105,7 @@ public Node copyRandomList(Node head) {
108
105
cur = cur. next;
109
106
h = h. next;
110
107
}
111
- return map. get(head. val );
108
+ return map. get(head);
112
109
}
113
110
```
114
111
@@ -139,8 +136,7 @@ public Node copyRandomList(Node head) {
139
136
Node l2 = null ;
140
137
// 生成所有的节点,并且分别插入到原有节点的后边
141
138
while (l1 != null ) {
142
- l2 = new Node ();
143
- l2. val = l1. val;
139
+ l2 = new Node (l1. val);
144
140
l2. next = l1. next;
145
141
l1. next = l2;
146
142
l1 = l1. next. next;
@@ -197,8 +193,7 @@ public Node copyRandomList(Node head) {
197
193
// 生成所有的节点,讲它们保存到原链表的 random 域,
198
194
// 同时利用新生成的节点的 next 域保存原链表的 random。
199
195
while (l1 != null ) {
200
- l2 = new Node ();
201
- l2. val = l1. val;
196
+ l2 = new Node (l1. val);
202
197
l2. next = l1. random;
203
198
l1. random = l2;
204
199
l1 = l1. next;
@@ -226,4 +221,5 @@ public Node copyRandomList(Node head) {
226
221
227
222
# 总
228
223
229
- 解法一、解法二是比较直接的想法,直接利用 ` HashMap ` 存储之前的节点。解法三、解法四利用原有链表的指针,通过指来指去完成了赋值。链表操作的核心思想就是,在改变某一个节点的指针域的时候,一定要把该节点的指针指向的节点用另一个指针保存起来,以免造成丢失。
224
+ 解法一、解法二是比较直接的想法,直接利用 ` HashMap ` 存储之前的节点。解法三、解法四利用原有链表的指针,通过指来指去完成了赋值。链表操作的核心思想就是,在改变某一个节点的指针域的时候,一定要把该节点的指针指向的节点用另一个指针保存起来,以免造成丢失。
225
+
0 commit comments