从大一学c开始接触了不少常用的排序算法,今天有空简单整理一下,希望对大家的学习有所帮助:
1.快速排序:
快速排序由C. A. R. Hoare在1962年提出。它的基本思想是:通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有数据都要小,然后再按此方法对这两部分数据分别进行快速排序,整个排序过程可以递归进行,以此达到整个数据变成有序序列。
#include<iostream>
using namespace std;
void qsort(int a[], int b, int e) {
if (e> b) {
int i= b, j= e, k= a[b];
while (i< j) {
while (i< j&&a[j]>= k) j--;
a[i]= a[j];
while (i< j&&a[i]<= k) i++;
a[j]= a[i];
}
a[i]= k;
qsort(a, b, i- 1);
qsort(a, i+ 1, e);
}
}
main() {
int a[6];
for (int i= 0; i< 6; i++) cin>> a[i];
qsort(a, 0, 5);
for (int i= 0; i< 6; i++) cout<< a[i]<< "-";
}
另一种分治形式:
#include<iostream>
using namespace std;
void swap(int *a, int* b) {
if (a!= b) {
*a= *a^ *b;
*b= *a^ *b;
*a= *a^ *b;
}
}
int partion(int a[], int s, int e) {
int j= s- 1;
for (int i= s; i< e; i++) {
if (a[i]< a[e]) {
j++;
swap(&a[i], &a[j]);
}
}
swap(&a[j+ 1], &a[e]);
return j+ 1;
}
void qsort(int a[], int s, int e) {
if (s< e) {
int m= partion(a, s, e);
qsort(a, s, m- 1);
qsort(a, m+ 1, e);
}
}
main() {
int a[5]= {3, 0, 5, 1, 55};
qsort(a, 0, 4);
for (int i= 0; i< 5; i++) cout<< a[i]<< "-";
}
尾递归优化:
快排算法和大多数分治排序算法一样,都有两次递归调用。但是快排与归并排序不同,归并的递归则在函数一开始, 快排的递归在函数尾部,这就使得快排代码可以实施尾递归优化。第一次递归以后,变量p就没有用处了, 也就是说第二次递归可以用迭代控制结构代替。虽然这种优化一般是有编译器实施,但是也可以人为的模拟:
采用这种方法可以缩减堆栈深度,由原来的O(n)缩减为O(logn)。
2.归幷排序:
归并排序(MERGE-SORT)是建立在归并操作上的一种有效的排序算法,该算法是采用分治法(Divide and Conquer)的一个非常典型的应用。将已有序的子序列合并,得到完全有序的序列;即先使每个子序列有序,再使子序列段间有序。若将两个有序表合并成一个有序表,称为二路
归并。
归并过程为:比较a[i]和a[j]的大小,若a[i]≤a[j],则将第一个有序表中的元素a[i]复制到r[k]中,并令i和k分别加上1;否则将第二个有序表中的元素a[j]复制到r[k]中,并令j和k分别加上1,如此循环下去,直到其中一个有序表取完,然后再将另一个有序表中剩余的元素复制到r中从下标k到下标t的单元。归并排序的算法我们通常用递归实现,先把待排序区间[s,t]以中点二分,接着把左边子区间排序,再把右边子区间排序,最后把左区间和右区间用一次归并操作合并成有序的区间[s,t]。
#include<iostream>
using namespace std;
void merge(int a[], int t[], int s, int m, int e) {
int i= s, k= s, j= m+ 1;
while (i!= m+ 1&&j!= e+ 1) {
if (a[i]>= a[j]) {
t[k++]= a[j++];
} else {
t[k++]= a[i++];
}
}
while (i!= m+ 1) t[k++]= a[i++];
while (j!= e+ 1) t[k++]= a[j++];
for (int i= s; i< e+ 1; i++) a[i]= t[i];
}
void mergesort(int a[], int t[], int s, int e) {
if (s< e) {
int m= (s+ e)/ 2;
mergesort(a, t, s, m);
mergesort(a, t, m+ 1, e);
merge(a, t, s, m, e);
}
}
main() {
int t[6], a[6]= {7, 3, 4, 1, 8, 0};
mergesort(a, t, 0, 5);
for (int i= 0; i< 6; i++) cout<< a[i]<< "-";
}