返回
划分为二:精解 LeetCode 第 86 号问题「分割链表」
见解分享
2024-01-06 19:24:58
引言
链表是一种重要的数据结构,在计算机科学和软件开发中广泛使用。LeetCode 第 86 号问题「分割链表」考查了我们对链表操作的理解和解决问题的能力。
问题陈述
给定一个链表和一个特定值 x,对链表进行分隔,使得所有小于 x 的节点都在大于或等于 x 的节点之前。链表中每个节点包含一个整数,且保证链表中至少有一个节点。
示例
输入:
head = [1,4,3,2,5,2]
x = 3
输出:
[1,2,2,4,3,5]
解题思路
为了解决这个问题,我们可以采用双指针法:
- 创建两个虚拟头结点: 分别指向小于 x 和大于或等于 x 的节点。
- 初始化两个指针: 一个指针指向原链表的第一个节点,另一个指针指向小于 x 节点的虚拟头结点。
- 遍历原链表:
- 若当前节点值小于 x,则将其插入到小于 x 节点的虚拟头结点后。
- 否则,将其插入到大于或等于 x 节点的虚拟头结点后。
- 合并两个链表: 将小于 x 节点的虚拟头结点的下一个节点指向大于或等于 x 节点的虚拟头结点的下一个节点。
- 返回小于 x 节点的虚拟头结点的下一个节点,即分割后的链表头结点。
代码实现
def partition(head, x):
# 创建虚拟头结点
less_dummy = ListNode(0)
greater_dummy = ListNode(0)
# 初始化指针
less = less_dummy
greater = greater_dummy
curr = head
# 遍历原链表
while curr:
if curr.val < x:
# 将小于 x 的节点插入到小于 x 节点的链表中
less.next = curr
less = less.next
else:
# 将大于或等于 x 的节点插入到大于或等于 x 节点的链表中
greater.next = curr
greater = greater.next
# 指向下一个节点
curr = curr.next
# 合并两个链表
less.next = greater_dummy.next
# 返回小于 x 节点的链表头结点
return less_dummy.next
复杂度分析
- 时间复杂度:O(n),其中 n 为链表的长度。
- 空间复杂度:O(1),因为我们只使用了常数个额外空间。
总结
通过采用双指针法,我们可以高效地解决 LeetCode 第 86 号问题「分割链表」。理解链表操作的基本原理和算法技巧对于解决此类问题至关重要。希望本文能够帮助你加深对链表操作的理解,提升你的算法解决能力。