题目描述
分析
利用归并排序来完成链表的排序
在归并过程中,断开链表,然后在合并新链表
算法
归并排序
过程
首先计算链表的总长度,在每次断开链表的时候,都是从中间断开,然后排序后再把两端接上
断开链表,分别进行排序
合并过程中,注意要挪动指针
算法
/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode} head
* @return {ListNode}
*/
var sortList = function (head) {
if (!head || !head.next) return head
let n = 0
let cur = head
while (cur) {
cur = cur.next
n++
}
return mergeSort(head, n)
}
function mergeSort(head, n) {
if (n <= 1) return head
const mid = n >> 1,
ret = new ListNode()
let p = ret,
p1 = head,
p2 = head
for (let i = 1; i < mid; i++) {
p2 = p2.next
}
const tmp = p2.next
p2.next = null
p2 = tmp
let l1 = mergeSort(head, mid)
let l2 = mergeSort(p2, n - mid)
while (l1 || l2) {
if (!l2 || (l1 && l1.val <= l2.val)) {
p.next = l1
l1 = l1.next
} else {
p.next = l2
l2 = l2.next
}
p = p.next
}
return ret.next
}