104 lines
2.3 KiB
Markdown
104 lines
2.3 KiB
Markdown
# 排序链表
|
||
|
||
## 题目
|
||
|
||
给你链表的头结点 head ,请将其按 升序 排列并返回 排序后的链表 。
|
||
|
||
|
||
|
||
示例 1:
|
||
|
||
|
||
输入:head = [4,2,1,3]
|
||
输出:[1,2,3,4]
|
||
示例 2:
|
||
|
||
|
||
输入:head = [-1,5,3,4,0]
|
||
输出:[-1,0,3,4,5]
|
||
示例 3:
|
||
|
||
输入:head = []
|
||
输出:[]
|
||
|
||
|
||
提示:
|
||
|
||
链表中节点的数目在范围 [0, 5 * 104] 内
|
||
-105 <= Node.val <= 105
|
||
|
||
|
||
进阶:你可以在 O(n log n) 时间复杂度和常数级空间复杂度下,对链表进行排序吗?
|
||
|
||
## 思路
|
||
|
||
- 归并排序
|
||
- 拆分
|
||
- 快慢指针
|
||
- 合并
|
||
|
||
|
||
## 代码
|
||
|
||
```java
|
||
/**
|
||
* Definition for singly-linked list.
|
||
* public class ListNode {
|
||
* int val;
|
||
* ListNode next;
|
||
* ListNode() {}
|
||
* ListNode(int val) { this.val = val; }
|
||
* ListNode(int val, ListNode next) { this.val = val; this.next = next; }
|
||
* }
|
||
*/
|
||
class Solution {
|
||
public ListNode sortList(ListNode head) {
|
||
// -- Divide -> Sort -> Merge --
|
||
// Special
|
||
if (head == null || head.next == null) {
|
||
return head;
|
||
}
|
||
|
||
// Init: slow, fast, dummyHead
|
||
ListNode dummyHead = new ListNode(-1);
|
||
dummyHead.next = head;
|
||
ListNode slow = dummyHead;
|
||
ListNode fast = dummyHead;
|
||
while (fast.next != null && fast.next.next != null) {
|
||
fast = fast.next.next;
|
||
slow = slow.next;
|
||
}
|
||
// Divide: [headA .... tailA(slow)] [headB(slow.next) ... tailB]
|
||
ListNode headA = head;
|
||
ListNode headB = slow.next;
|
||
slow.next = null;
|
||
// Sort
|
||
headA = sortList(headA);
|
||
headB = sortList(headB);
|
||
// Merge
|
||
return mergeList(headA, headB);
|
||
}
|
||
|
||
public ListNode mergeList(ListNode headA, ListNode headB) {
|
||
// Init: dummyHead, tail
|
||
ListNode dummyHead = new ListNode(-1);
|
||
ListNode tail = dummyHead;
|
||
// Traverse: Merge
|
||
while (headA != null && headB != null) {
|
||
int valA = headA.val;
|
||
int valB = headB.val;
|
||
if (valA < valB) {
|
||
tail.next = headA;
|
||
headA = headA.next;
|
||
} else {
|
||
tail.next = headB;
|
||
headB = headB.next;
|
||
}
|
||
tail = tail.next;
|
||
}
|
||
// Operation: After
|
||
tail.next = headA == null ? headB : headA;
|
||
return dummyHead.next;
|
||
}
|
||
}
|
||
``` |