文章目录
- 链表的排序:插入排序和归并排序
- 147. 对链表进行插入排序
- 148. 排序链表
链表的排序:插入排序和归并排序
两道例题进行记录。
147. 对链表进行插入排序
题目链接:https://leetcode.cn/problems/insertion-sort-list/
题目大意:给定单个链表的头 head ,使用 插入排序 对链表进行排序,并返回 排序后链表的头 。
插入排序 算法的步骤:
插入排序是迭代的,每次只移动一个元素,直到所有元素可以形成一个有序的输出列表。
每次迭代中,插入排序只从输入数据中移除一个待排序的元素,找到它在序列中适当的位置,并将其插入。
重复直到所有输入数据插入完为止。
下面是插入排序算法的一个图形示例。部分排序的列表(黑色)最初只包含列表中的第一个元素。每次迭代时,从输入数据中删除一个元素(红色),并就地插入已排序的列表中。
对链表进行插入排序。
注意:(1)列表中的节点数在 [1, 5000]范围内;(2)-5000 <= Node.val <= 5000
示例:
输入: head = [4,2,1,3]
输出: [1,2,3,4]
参考代码:
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def insertionSortList(self, head: Optional[ListNode]) -> Optional[ListNode]:
if not head: return head
dummyHead = ListNode(0)
dummyHead.next = head
lastSorted = head
curr = head.next
while curr:
if lastSorted.val <= curr.val:
lastSorted = lastSorted.next
else:
prev = dummyHead
while prev.next.val <= curr.val:
prev = prev.next
lastSorted.next = curr.next
curr.next = prev.next
prev.next = curr
curr = lastSorted.next
return dummyHead.next
148. 排序链表
题目链接:https://leetcode.cn/problems/insertion-sort-list/
题目大意:
给你链表的头结点 head ,请将其按 升序 排列并返回 排序后的链表 。
注意:(1)链表中节点的数目在范围 [0,
5
∗
1
0
4
5 * 10^4
5∗104] 内;(2)
−
1
0
5
-10^5
−105 <= Node.val <=
1
0
5
10^5
105
示例:
输入:head = [4,2,1,3]
输出:[1,2,3,4]
参考代码:
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def sortList(self, head: Optional[ListNode]) -> Optional[ListNode]:
if not head or not head.next: return head
# 区别于 876.链表的中间结点 我们需要的是全部分开 便是两个
# 当递归至只有两个元素时 fast = head.next 可以避免原地踏步
# 如果 slow,fast = head,head 只有两个元素时,
# 两个指针会原地踏步 令程序陷入死循环
slow,fast = head,head.next
while fast and fast.next:
fast,slow = fast.next.next,slow.next
# 把 长串 分解成为小串 断开后面的内容
mid,slow.next = slow.next,None
left,right = self.sortList(head),self.sortList(mid)
# 合并 left 和 right
cur = dummy = ListNode(0)
while left and right:
if left.val < right.val:
cur.next,left = left,left.next
else:
cur.next,right = right,right.next
cur = cur.next
cur.next = left if left else right
return dummy.next