归并排序,就是将一个链表不断二分,排好序后,再将两个链表归并起来。
数组版:
void merge_sort(int *&A, int x, int y, int* T)
{
if (y-x > 1)
{
int m = x + (y-x) / 2;
int p = x, q = m, i = x;
merge_sort(A, x, m, T); //递归求解
merge_sort(A, m, y, T);
while (p < m || q < y)
{
if(q >= y || (p < m && A[p] <= A[q])) /* (p < m && A[p] <= A[q])如果左边小于右边,就复制到T
如果p<m而且q>=y,就是数组q为空,数组p剩余,复制给T。 */
T[i++] = A[p++];
else T[i++] = A[q++]; //否则复制右边的到T
}
for(i=x; i<y; i++) A[i] = T[i]; // 把T复制回A
}
}
链表版:
struct linkedlist{
int data;
linkedlist *next;
};
linkedlist* divide(linkedlist *head) //将一个链表分成两半
{
linkedlist *pos,*second, *mid=head;
if(head==NULL) return NULL;
pos = mid->next;
while(pos!=NULL){ //mid用于寻找中间的结点
pos=pos->next;
if(pos!=NULL){
mid=mid->next;
pos=pos->next;
}
}
second = mid->next;
mid->next = NULL;
return second;
}
linkedlist* merge(linkedlist *one,linkedlist *two) //对两个链表进行归并排序
{
linkedlist *lastsorted;
linkedlist com;
lastsorted = &com;
while(one != NULL && two != NULL){
if(one->data <= two->data){
lastsorted->next = one;
lastsorted = one;
one = one->next;
}
else{
lastsorted->next = two;
lastsorted = two;
two = two->next;
}
}
if(one == NULL) lastsorted->next = two;
else lastsorted->next = one;
return com.next;
}
void mergesort(linkedlist *&head)
{
if(head!=NULL && head->next!=NULL){
linkedlist *second = divide(head);
mergesort(head);
mergesort(second);
head = merge(head,second);
}
}