42
42
43
43
### 方法一:拼接链表
44
44
45
- 创建两个链表,一个存放小于 ` x ` 的节点,另一个存放大于等于 ` x ` 的节点,之后进行拼接即可。
45
+ 我们创建两个链表 $left$ 和 $right$,分别用于存储小于 $x$ 的节点和大于等于 $x$ 的节点。
46
+
47
+ 然后我们用两个指针 $p1$ 和 $p2$ 分别指向 $left$ 和 $right$ 的最后一个节点,初始时 $p1$ 和 $p2$ 都指向一个虚拟头节点。
48
+
49
+ 接下来我们遍历链表 $head$,如果当前节点的值小于 $x$,我们就将当前节点添加到 $left$ 链表的末尾,即 $p1.next = head$,然后令 $p1 = p1.next$;否则我们就将当前节点添加到 $right$ 链表的末尾,即 $p2.next = head$,然后令 $p2 = p2.next$。
50
+
51
+ 遍历结束后,我们将 $left$ 链表的尾节点指向 $right$ 链表的第一个有效节点,即 $p1.next = right.next$,然后将 $right$ 链表的尾节点指向空节点,即 $p2.next = null$。
52
+
53
+ 最后我们返回 $left$ 链表的第一个有效节点。
54
+
55
+ 时间复杂度 $O(n)$,其中 $n$ 是链表的长度。空间复杂度 $O(1)$。
46
56
47
57
<!-- tabs:start -->
48
58
56
66
57
67
class Solution :
58
68
def partition (self , head : ListNode, x : int ) -> ListNode:
59
- l1, l2 = ListNode(0 ), ListNode(0 )
60
- cur1, cur2 = l1, l2
69
+ left, right = ListNode(0 ), ListNode(0 )
70
+ p1, p2 = left, right
61
71
while head:
62
72
if head.val < x:
63
- cur1 .next = head
64
- cur1 = cur1 .next
73
+ p1 .next = head
74
+ p1 = p1 .next
65
75
else :
66
- cur2 .next = head
67
- cur2 = cur2 .next
76
+ p2 .next = head
77
+ p2 = p2 .next
68
78
head = head.next
69
- cur1 .next = l2 .next
70
- cur2 .next = None
71
- return l1 .next
79
+ p1 .next = right .next
80
+ p2 .next = None
81
+ return left .next
72
82
```
73
83
74
84
``` java
@@ -77,29 +87,27 @@ class Solution:
77
87
* public class ListNode {
78
88
* int val;
79
89
* ListNode next;
80
- * ListNode() {}
81
- * ListNode(int val) { this.val = val; }
82
- * ListNode(int val, ListNode next) { this.val = val; this.next = next; }
90
+ * ListNode(int x) { val = x; }
83
91
* }
84
92
*/
85
93
class Solution {
86
94
public ListNode partition (ListNode head , int x ) {
87
- ListNode l1 = new ListNode (0 );
88
- ListNode l2 = new ListNode (0 );
89
- ListNode cur1 = l1, cur2 = l2;
90
- while (head != null ) {
95
+ ListNode left = new ListNode (0 );
96
+ ListNode right = new ListNode (0 );
97
+ ListNode p1 = left;
98
+ ListNode p2 = right;
99
+ for (; head != null ; head = head. next) {
91
100
if (head. val < x) {
92
- cur1 . next = head;
93
- cur1 = cur1 . next;
101
+ p1 . next = head;
102
+ p1 = p1 . next;
94
103
} else {
95
- cur2 . next = head;
96
- cur2 = cur2 . next;
104
+ p2 . next = head;
105
+ p2 = p2 . next;
97
106
}
98
- head = head. next;
99
107
}
100
- cur1 . next = l2 . next;
101
- cur2 . next = null ;
102
- return l1 . next;
108
+ p1 . next = right . next;
109
+ p2 . next = null ;
110
+ return left . next;
103
111
}
104
112
}
105
113
```
@@ -110,35 +118,58 @@ class Solution {
110
118
* struct ListNode {
111
119
* int val;
112
120
* ListNode *next;
113
- * ListNode() : val(0), next(nullptr) {}
114
- * ListNode(int x) : val(x), next(nullptr) {}
115
- * ListNode(int x, ListNode *next) : val(x), next(next) {}
121
+ * ListNode(int x) : val(x), next(NULL) {}
116
122
* };
117
123
*/
118
124
class Solution {
119
125
public:
120
126
ListNode* partition(ListNode* head, int x) {
121
- ListNode* l1 = new ListNode();
122
- ListNode* l2 = new ListNode();
123
- ListNode* cur1 = l1 ;
124
- ListNode* cur2 = l2 ;
125
- while ( head != nullptr ) {
127
+ ListNode* left = new ListNode(0 );
128
+ ListNode* right = new ListNode(0 );
129
+ ListNode* p1 = left ;
130
+ ListNode* p2 = right ;
131
+ for (; head; head = head->next ) {
126
132
if (head->val < x) {
127
- cur1 ->next = head;
128
- cur1 = cur1 ->next;
133
+ p1 ->next = head;
134
+ p1 = p1 ->next;
129
135
} else {
130
- cur2 ->next = head;
131
- cur2 = cur2 ->next;
136
+ p2 ->next = head;
137
+ p2 = p2 ->next;
132
138
}
133
- head = head->next;
134
139
}
135
- cur1 ->next = l2 ->next;
136
- cur2 ->next = nullptr;
137
- return l1 ->next;
140
+ p1 ->next = right ->next;
141
+ p2 ->next = nullptr;
142
+ return left ->next;
138
143
}
139
144
};
140
145
```
141
146
147
+ ```go
148
+ /**
149
+ * Definition for singly-linked list.
150
+ * type ListNode struct {
151
+ * Val int
152
+ * Next *ListNode
153
+ * }
154
+ */
155
+ func partition(head *ListNode, x int) *ListNode {
156
+ left, right := &ListNode{}, &ListNode{}
157
+ p1, p2 := left, right
158
+ for ; head != nil; head = head.Next {
159
+ if head.Val < x {
160
+ p1.Next = head
161
+ p1 = p1.Next
162
+ } else {
163
+ p2.Next = head
164
+ p2 = p2.Next
165
+ }
166
+ }
167
+ p1.Next = right.Next
168
+ p2.Next = nil
169
+ return left.Next
170
+ }
171
+ ```
172
+
142
173
``` ts
143
174
/**
144
175
* Definition for singly-linked list.
@@ -153,30 +184,23 @@ public:
153
184
*/
154
185
155
186
function partition(head : ListNode | null , x : number ): ListNode | null {
156
- if (head == null) {
157
- return head;
158
- }
159
- let cur = head;
160
- while (cur.next != null) {
161
- let node = cur.next;
162
- if (node.val < x) {
163
- [head, node.next, cur.next] = [node, head, node.next];
187
+ const [left, right] = [new ListNode (), new ListNode ()];
188
+ let [p1, p2] = [left , right ];
189
+ for (; head ; head = head .next ) {
190
+ if (head .val < x ) {
191
+ p1 .next = head ;
192
+ p1 = p1 .next ;
164
193
} else {
165
- cur = cur.next;
194
+ p2 .next = head ;
195
+ p2 = p2 .next ;
166
196
}
167
197
}
168
- return head;
198
+ p1 .next = right .next ;
199
+ p2 .next = null ;
200
+ return left .next ;
169
201
}
170
202
```
171
203
172
204
<!-- tabs: end -->
173
205
174
- ### 方法二:头插法
175
-
176
- 题中指出,** 不需要保留节点的相对位置** 。
177
-
178
- 1 . 遍历链表。
179
- 2 . 当节点符合小于 ` x ` 条件时,将其移动至头节点前方,成为新的头节点。
180
- 3 . 忽略大于等于 ` x ` 的节点。
181
-
182
206
<!-- end -->
0 commit comments