标签:
冒泡
交换相邻的点使得最小的点排到最前,同时后面的点一定程度上也排序。
#include<iostream> #include<string> using namespace std; void Bubble(int *list,int length) { bool flag=true; for(int i=0;i<=length-1&&flag;i++) { flag=false; for(int j=length-1;j>=i+1;j--) { if(list[j]<list[j-1]) { int temp=list[j]; list[j]=list[j-1]; list[j-1]=temp; flag=true; } } } }
简单选择
查找最小的点,把它放到最前面。
void SelectSort(int * list ,int length) { for(int i=0;i<length-1;i++) { int min=i; for(int j=i+1;j<length;j++) { if(list[j]<list[min]) { min=j; } } if(i!=min) { int temp=list[min]; list[min]=list[i]; list[i]=temp; } } }
直接插入
将第i+1个点插入到已排好序的前i个点中。
void InsertSort(int* list ,int length) { for(int i=1;i<length;i++)//已经排好前i个数,处理第i+1个即下标i的 { int j=i-1;//前i个中的最后一个的下标 int tempi=list[i]; for(;j>=0&&tempi<list[j];j--) { list[j+1]=list[j]; } list[j+1]=tempi; } }
希尔
其实有点类似直接插入,是分成好几组进行的。增量序列为dlta[k]=2t-k+1-1(0<=k<=t<=log2(n+1))。
第一层do while循环是increment逐次减一,直到increment为1
第二层for循环是比较i和i+increment项,i从头到尾
第三层for循环是为了移动,将比第i+increment项大的都向后移
void ShellSort(int*list,int length) { int increment=length/3+1; do { increment=increment/3+1; for(int i=0;i<=length-increment-1;++i) { int temp=list[i+increment]; int j=i; for(;j>=0&&temp<list[j];j-=increment) { list[j+increment]=list[j]; } list[j+increment]=temp; } }while(increment>1); }
堆排序
先构建最大堆,即先将子树变成最大堆,交换1号和最后一个,再将去掉最后一个的序列调整成最大堆
void heapcore(int *list,int s,int m) { int temp=list[s]; int j=2*s; for(;j<=m;j*=2) { if(j<m&&list[j]<list[j+1]) j++; if(temp>=list[j]) break; list[j/2]=list[j]; list[j]=temp; } } void HeapSort(int*list ,int length) { for(int i=(length-1)/2;i>=1;--i) { heapcore(list,i,length-1); } for(int i=length-1;i>=2;--i) { int temp=list[1]; list[1]=list[i]; list[i]=temp; heapcore(list,1,i-1); } }
快速
先随机选择一个数,将小于它的放在左边,大于的放在右边。返回该数的位置,然后处理左边序列,右边序列其中放置其他数的方法是,设置一个small标志,从start开始,遇到比轴小的就交换i和small位置的数,small加1
int partition(int *list ,int start,int end) { int idex=rand()%(end-start+1)+start; int small=start; int key=list[idex]; list[idex]=list[end]; list[end]=key; for(int i=start;i<end;i++) { if(list[i]<key) { int temp=list[small]; list[small]=list[i]; list[i]=temp; small++; } } int temp=list[small]; list[small]=list[end]; list[end]=temp; return small; } void QSort(int*list,int start,int end) { int id=partition(list ,start,end); if(id>start) QSort(list,start,id-1); if(id<end) QSort(list,id+1,end); } void QuickSort(int*list,int length) { QSort(list,0,length-1); }
归并
先两个两个的,再四个四个的,后八个八个的排。。。
//排s1~s2-1(有序),s2~end(有序)两段,排好放在temp void Merge(int *list,int *temp,int s1,int s2,int end ) { int i=s1; int j=s2; int k=s1; while(i<=s2-1&&j<=end) { if(list[i]<list[j]) { temp[k]=list[i]; i++; k++; } else { temp[k]=list[j]; j++; k++; } } if(i<=s2-1) { while(i<=s2-1) { temp[k]=list[i]; i++; k++; } } if(j<=end) { while(j<=end) { temp[k]=list[j]; j++; k++; } } } //从第0个开始,相邻两个k个合并,即0~k-1,k~2k-1合并,2k~3k-1,3k~4k-1合并。。。 void MSort(int*list,int *temp,int k,int length) { int i=0; //i是第一个k个的第一个i+2k-1是第二个k个的最后一个,要保证在长度范围内 for(;i+2*k-1<=length-1;i=i+2*k) { Merge(list,temp,i,i+k,i+2*k-1); } //剩下的不足2k个,可能>k&&<2k或者<=k //i+k-1是第二个k个的第一个,说明存在第二个k个,需要合并 if(i+k-1<=length-1) { Merge(list,temp,i,i+k,length-1); } //不足k个,不用合并,直接复制 else { for(int j=i;j<=length-1;j++) temp[j]=list[i]; } } void MergeSort(int*list,int length) { int *temp=new int[length]; int k=1; while(k<length) { //这样做主要是为了将temp合并到list里面 MSort(list,temp,k,length); k*=2; MSort(temp,list,k,length); k*=2; } delete[] temp; }
int main() { int a[1000]; int i=0; int c; while(cin>>c) { a[i]=c; i++; if(cin.get()==‘\n‘) break; } //Bubble(a,i); //SelectSort(a,i); //InsertSort(a,i); //ShellSort(a,i); //HeapSort(a,i); //QuickSort(a,i); MergeSort(a,i); for(int j=0;j<i;j++) { cout<<a[j]<<" "; } }
标签:
原文地址:http://www.cnblogs.com/zhangyee/p/4712526.html