简单选择排序
每次从n个数中选择最小的一个放在还未排序的数的最前面,共n-1次。- 算法复杂度O(n²)
直接插入排序
每次将待排序的数插入在已排序的数中,共n-1次。- 算法复杂度:O(n) - O(n²)
冒泡排序
每次比较相邻两个元素的值,如果前者大于后者,则交换。一趟之后,最大的元素沉底。共n-1趟。如果每趟没有发生交换,则说明已经排好。- 算法复杂度:O(n) - O(n²)
快速排序
假设选择第一个数字为基准数,指针i从前向后移动,指针j从后向前移动。i在移动时指向一个大于基准数的值,j指向一个小于基准数的值,此时,若i<=j时,交换两个指针的值,之后继续移动指针、判断、交换。当i>j时,将j指向的值和基准数交换。- 算法复杂度:O(nlogn) - O(n²)
#include<iostream>
#include<fstream>
#include<ctime>
#include<stdlib.h>
using namespace std;
#define SIZE 50 //200,000个数据
/*
int time()
{
time_t t0;
time(&t0);
cout<<t0;
return t1-t0;
}*/
void Swap(int &a,int &b)
{
int temp;
temp=a;
a=b;
b=temp;
}
template <class T>
void SelectSort(int A[], int n)
{
int small;
for (int i=0; i<n-1; i++)
{ //执行n-1趟
small=i; //先假定待排序序列中第一个元素为最小
for (int j=i+1;j<n;j++) //每趟扫描待排序序列n-i-1次
if (A[j]<A[small]) small=j; //如果扫描到一个比最小值元素还小的,则记下其下标
Swap(A[i],A[small]); //最小元素与待排序序列中第一个元素交换
}
}
template <class T>
void InsertSort(T A[], int n)
{
for(int i=1; i<n; i++){ //执行n-1趟
int j=i;
T temp=A[i]; //待插入元素存入临时变量
while(j>0&&temp<A[j-1])
{ //从后往前查找插入位置
A[j]=A[j-1];
j--; //A[j-1]元素后移,j指针前移
}
A[j]=temp; //待插入元素存入找到的插入位置
}
}
template <class T>
void BubbleSort(T A[], int n)
{
int i,j,last;
i=n-1;
while (i>0){ //最多进行n-1趟
last=0; //进入循环就将last置成0
for (j=0; j<i; j++) //从上往下进行相邻元素的两两比较
if (A[j+1]<A[j]){
Swap(A[j],A[j+1]); //由于后者小,故交换
last=j; //有交换就将last置成j
}
i=last; //如果一趟排序中没有交换元素,则last为0
}
}
template <class T>
void QuickSort(T A[], int n)
{
QSort(A,0,n-1); //以初始序列为待排序序列开始快速排序
}
template <class T>
void QSort(T A[], int left, int right) //left和right为待排序序列的下界和上界
{
int i,j;
if (left<right){ //若待排序序列多于一个元素,则继续快速排序
i=left; j=right+1; //确定待排序序列的游动指针i,j
do{ //开始一趟快速排序,A[left]作为分割元素
do i++;while (A[i]<A[left]); //i指针从左往右找第一个分割元素的元素
do j--; while (A[j]>A[left]);//j指针从右往左找第一个分割元素的元素
if (i<j) Swap(A[i],A[j]); //若i<j,则交换两个元素
}while (i<j); //若i<j,则继续本趟排序
Swap(A[left],A[j]); //交换分割元素A[left]和A[j]的位置
QSort(A,left,j-1); //对低端序列快速排序
QSort(A,j+1,right); //对高端序列快速排序
}
}
template <class T>
void Merge(T A[],int i1,int j1,int i2,int j2)
{ // i1,j1是子序列1的下、上界,i1,j2是子序列2的下、上界
T *Temp=new T[j2-i1+1]; //分配能存放两个子序列的临时数组
int i=i1,j=i2,k=0; //i,j是两个子序列的游动指针,k是Temp的游动指针
while (i<=j1&&j<=j2) //若两个子序列都不空,则循环
if (A[i]<=A[j]) Temp[k++]=A[i++]; //将A[i]和A[j]中较小的存入Temp[k]
else Temp[k++]=A[j++];
while (i<=j1) Temp[k++]=A[i++]; //若第一个子序列中还有剩余的就存入Temp
while (j<=j2) Temp[k++]=A[j++]; //若第二个子序列中还有剩余的就存入Temp
for (i=0; i<k; i++) A[i1++]=Temp[i]; //将临时数组中的元素倒回A
delete [] Temp;
}
template <class T>
void MergeSort(T A[], int n)
{
int i1,j1,i2,j2; //i1,j1是子序列1的下、上界,i2,j2是子序列2的下、上界
int size=1; //子序列中元素个数,初始化为1。
while (size<n){
i1=0;
while (i1+size<n){ //若i1+size<n,则说明存在两个子序列,需再两两合并
i2=i1+size; //确定子序列2的下界
j1=i2-1; //确定子序列1的上界
if (i2+size-1>n-1)
j2=n-1; //若第2个子序列中不足size个元素,则置子序列2的上界j2=n-1
else j2=i2+size-1; //否则有size个,置j2=i2+size-1
Merge(A,i1,j1,i2,j2); //合并相邻两个子序列 i1=j2+1; //确定下一次合并第一个子序列的下界
}
size*=2; //元素个数扩大一倍
}
}
template <class T>
void AdjustDown(T A[], int r, int j)
{
int child=2*r+1; T temp=A[r];
while(child<=j) {
if((child<j)&&(A[child]<A[child+1])) child++; //找两个孩子中较大的孩子
if (temp>= A[child]) break;
A[(child-1)/2]=A[child];
child=2*child+1;
}
A[(child-1)/2]=temp;
}
template <class T>
void HeapSort(T A[], int n)
{
for(int i=(n-2)/2; i>-1; i--)
AdjustDown(A,i,n-1); //构造最大堆
for(int i=n-1; i>0; i--)
{
Swap(A[0],A[i]); //堆顶和堆底元素交换位置
AdjustDown(A,0,i-1); //将A[0]向下调整为堆
}
}
int main()
{
int a[SIZE];
time_t t0,t1;
/*SelectSort*/
for(int i=0;i<SIZE;i++)
{
a[i]=rand()%SIZE;
}
time(&t0);
SelectSort<int>(a,SIZE);
time(&t1);
cout<<"SelectSort:"<<t1-t0<<endl;
for(int i=0;i<SIZE;i++)
{
cout<<a[i]<<" ";
}
/*InsertSort*/
for(int i=0;i<SIZE;i++)
{
a[i]=rand()%SIZE;
}
time(&t0);
InsertSort<int>(a,SIZE);
time(&t1);
cout<<"InsertSort:"<<t1-t0<<endl;
for(int i=0;i<SIZE;i++)
{
cout<<a[i]<<" ";
}
/*BubbleSort*/
for(int i=0;i<SIZE;i++)
{
a[i]=rand()%SIZE;
}
time(&t0);
BubbleSort<int>(a,SIZE);
time(&t1);
cout<<"BubbleSort:"<<t1-t0<<endl;
for(int i=0;i<SIZE;i++)
{
cout<<a[i]<<" ";
}
/*QuickSort*/
for(int i=0;i<SIZE;i++)
{
a[i]=rand()%SIZE;
}
time(&t0);
QuickSort<int>(a,SIZE);
time(&t1);
cout<<"QuickSort:"<<t1-t0<<endl;
for(int i=0;i<SIZE;i++)
{
cout<<a[i]<<" ";
}
/*HeapSort*/
for(int i=0;i<SIZE;i++)
{
a[i]=rand()%SIZE;
}
time(&t0);
HeapSort<int>(a,SIZE);
time(&t1);
cout<<"HeapSort:"<<t1-t0<<endl;
/*MergeSort*/
for(int i=0;i<SIZE;i++)
{
a[i]=rand()%SIZE;
}
time(&t0);
MergeSort<int>(a,SIZE);
time(&t1);
cout<<"MergeSort:"<<t1-t0<<endl;
for(int i=0;i<SIZE;i++)
{
cout<<a[i]<<" ";
}
return 0;
}