给你链表的头结点 head ,请将其按 升序 排列并返回 排序后的链表 。
进阶:
你可以在 O(n log n) 时间复杂度和常数级空间复杂度下,对链表进行排序吗?
示例 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
通过次数165,124提交次数246,594
1.自下而上的归并排序
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode() : val(0), next(nullptr) {}
* ListNode(int x) : val(x), next(nullptr) {}
* ListNode(int x, ListNode *next) : val(x), next(next) {}
* };
*/
class Solution {
public:
ListNode* sortList(ListNode* head) {
return sortList(head,NULL);
}
ListNode *sortList(ListNode*head,ListNode*tail){
if(head==NULL){
return head;
}
if(head->next==tail){
head->next=NULL;
return head;
}
ListNode*p=head;
ListNode*q=head;
while(q!=tail){
p=p->next;
q=q->next;
if(q!=tail){
q=q->next;
}
}
// cout<<"cea"<<" "<<head->val<<" "<<p->val<<endl;
return merge(sortList(head,p),sortList(p,tail));
}
ListNode *merge(ListNode*l1,ListNode*l2){
ListNode *head=new ListNode();
ListNode *q=new ListNode();
q=head;
head->next=l1;
while(l1&&l2){
if(l2->val<=l1->val){
q->next=new ListNode(l2->val,l1);
q=q->next;
l2=l2->next;
}
else{
q=l1;
l1=l1->next;
}
}
while(l1){
q=l1;
l1=l1->next;
}
q->next=l2;
ListNode*p=head->next;
return head->next;
//return l1;
}
};
2.自上而下
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode() : val(0), next(nullptr) {}
* ListNode(int x) : val(x), next(nullptr) {}
* ListNode(int x, ListNode *next) : val(x), next(next) {}
* };
*/
class Solution {
public:
ListNode* sortList(ListNode* head) {
//如果是空链表 直接返回
if (head==NULL) {
return head;
}
//求出链表长度
int length=0;
ListNode* node=head;
while (node) {
length++;
node=node->next;
}
//设置虚拟头节点
ListNode* dummyHead = new ListNode(0, head);
for (int subLength=1;subLength<length;subLength<<= 1) {
ListNode* prev = dummyHead, *curr = dummyHead->next;
while(curr) {
//左边
ListNode* head1 = curr;
for (int i=1; i<subLength&&curr->next; i++) {
curr=curr->next;
}
//右边
ListNode* head2 = curr->next;
//将左边断掉
curr->next=NULL;
curr = head2;
//右边可能不够长
for (int i=1; i<subLength&&curr&&curr->next; i++) {
curr=curr->next;
}
ListNode* next=NULL;
if (curr){
//下一个要合并的小数组
next=curr->next;
//将右边断掉
curr->next=NULL;
}
//合并
ListNode* merged = merge(head1, head2);
//新的头
prev->next = merged;
//移到新的头的最后一个位置
while (prev->next) {
prev = prev->next;
}
curr = next;
}
}
return dummyHead->next;
}
ListNode *merge(ListNode*l1,ListNode*l2){
ListNode *head=new ListNode();
ListNode *q=new ListNode();
q=head;
head->next=l1;
while(l1&&l2){
if(l2->val<=l1->val){
q->next=new ListNode(l2->val,l1);
q=q->next;
l2=l2->next;
}
else{
q=l1;
l1=l1->next;
}
}
while(l1){
q=l1;
l1=l1->next;
}
q->next=l2;
ListNode*p=head->next;
return head->next;
//return l1;
}
};