1.链表的排序
有快排和归并两种排法 力扣上面提交快排会超时
我们使用归并排序;归并排序的核心思想是分治法
先分:将链表分成两个部分 可以使用快慢指针法 快指针走两格慢指针走一格
再将两个链表分成两个部分 直到每个链表只有一个结点为止
治:用到之前的排序 因为只有一个结点所以每个结点都有序 用到昨天合并有序链表的思路合并链表
附上C语言的代码:
struct ListNode* merge_sotrlist(struct ListNode* p,struct ListNode* q){
struct ListNode *head=(struct ListNode*)malloc(sizeof(struct ListNode));
struct ListNode *temp=head;
while(p!=NULL&&q!=NULL){
if(p->val<=q->val){
temp->next=p;
temp=p;
p=p->next;
}else{
temp->next=q;
temp=q;
q=q->next;
}
}
temp->next=(p==NULL)?q:p;
return head->next;
}
struct ListNode* sortList(struct ListNode* head){
if(head==NULL||head->next==NULL)return head;
struct ListNode*p=head;
struct ListNode*q=head->next;
while(q!=NULL&&q->next!=NULL){
p=p->next;q=q->next->next;
}
q=p->next;
p->next=NULL;
return merge_sotrlist(sortList(head),sortList(q));
}
还有一种思路:将链表的数提取出来用快排后将数在存入链表中
数组快排可以使用qsort函数 stdlib.h下的封装
#define MAX_LEN 1000
int Cmp(const void *a, const void *b)
{
return *(int *)a - *(int *)b;
}
struct ListNode* sortList(struct ListNode* head)
{
struct ListNode *node = head;
int num = 0;
while (node != NULL) {
num++;
node = node->next;
}
int *tmpNum = (int *)calloc(num, sizeof(int));
node = head;
num = 0;
while (node != NULL) {
tmpNum[num++] = node->val;
node = node->next;
}
qsort(tmpNum, num, sizeof(int), Cmp);//数组名 个数 大小 比较函数
node = head;
num = 0;
while (node != NULL) {
node->val = tmpNum[num++];
node = node->next;
}
return head;
}