「这是我参与11月更文挑战的第8天,活动详情查看:2021最后一次更文挑战」
题目
给你一个链表的头节点 head 和一个特定值 x ,请你对链表进行分隔,使得所有 小于 x 的节点都出现在 大于或等于 x 的节点之前。
你应当保留两个分区中每个节点的初始相对位置。
示例 1:
输入: head = [1,4,3,2,5,2], x = 3
输出:[1,2,2,4,3,5]
力扣(LeetCode)链接:leetcode-cn.com/problems/pa…
解题思路
- 第一眼看完题就想着遍历一遍,找到把小于 x 的节点从原位置删除,加到前面。但是题目有要求保留每个节点原有的相对位置,所以不能这么干。
- 那就创建个新的链表,把小于 x 的节点放到新链表上,再把两个子链表拼接后返回。
- 既然小于 x 的那部分节点可以放到新链表上。那大于的那部分也可以放新链表上,这样省去了删除的操作,逻辑也更清晰,只是多了个头节点,和节点引用。
- 从主链表删除节点并添加到新链表操作步骤:
- 子链表尾节点指向新节点
- 遍历的指针后移
- 子链表尾节点后移
- 设置子链表尾节点的 next 为 null
代码实现
var partition = function(head, x) {
let largeHead = new ListNode(null, null)
let smallHead = new ListNode(null, null)
let largeEnd = largeHead //当前较大链表尾节点,默认指向大链表的头
let samllEnd = smallHead //当前较小链表尾节点,默认指向小链表的头
let curr = head
while (curr) {
if (curr.val < x) {
//当前节点的值小于x时
//1.当前节点加到较小链表的尾部
//2.较小链表尾节点后移
samllEnd.next = curr
samllEnd = samllEnd.next
} else {
largeEnd.next = curr
largeEnd = largeEnd.next
}
curr = curr.next
}
//更新最大尾节点的 next 为 null,防止出现环
largeEnd.next = null
//把小链表的最后一个节点指向大链表真实的头节点
samllEnd.next = largeHead.next
return smallHead.next
}
如有错误欢迎指出,欢迎一起讨论!