难度:中等 日期:2023年6月11日
给你链表的头结点
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 = [] 输出:[]
方法一:数组保存+排序
思路:将所有链表节点值保存在数组中,并对该数组排序,根据排序后的数组重新建立链表返回
var sortList = function(head) {
let arr = [];
let list = new ListNode(0,null);
for(let node = head;node !=null;node = node.next){
arr.push(node.val);
}
arr.sort((a,b)=>a-b);
let p = list;
for(let i = 0;i<arr.length;i++){
p.next = new ListNode(arr[i],null);
p = p.next;
}
return list.next
};
结果
方法二:自顶向下归并排序
思路:将链表从中心切分成两个链表,对这两个链表按节点值进行归并排序。递归的分别将这两个子链表进行分割 和 合并,使其变成有序链表,最后整个两个子链表
//合并
const merge = (head1, head2) => {
const dummyHead = new ListNode(0);
let temp = dummyHead, temp1 = head1, temp2 = head2;
while (temp1 !== null && temp2 !== null) {
if (temp1.val <= temp2.val) {
temp.next = temp1;
temp1 = temp1.next;
} else {
temp.next = temp2;
temp2 = temp2.next;
}
temp = temp.next;
}
if (temp1 !== null) {
temp.next = temp1;
} else if (temp2 !== null) {
temp.next = temp2;
}
return dummyHead.next;
}
//切分
const toSortList = (head, tail) => {
if(head == null || head.next == null) return head;
let slow = head,fast = head;
while(fast != tail && fast.next != tail && fast.next.next != null){
slow = slow.next;
fast = fast.next.next;
}
let mid = slow.next;
slow.next = null
return merge(toSortList(head,slow),toSortList(mid,tail));
}
var sortList = function(head) {
return toSortList(head, null);
};