#include <iostream> #include <vector> #include <string> #include <algorithm> #include <stdlib.h> using namespace std; #define MAXSIZE 20 #define LT(a,b) ((a)<(b)) #define LQ(a,b) ((a)<=(b)) #define ET(a,b) ((a)==(b)) #define left(x) (2*x+1) #define right(x) 2*(x+1) typedef int KeyType; //int i=0,j=0; typedef struct { KeyType key; //InfoType otherinfo; }RedType; typedef struct { RedType r[MAXSIZE+1]; int length; }SqList; bool is_friend(string a,string b) { if(a==b) return false; sort(a.begin(),a.end()); sort(b.begin(),b.end()); return a==b; } //void InsertSort(SqList &L) //{ // for (i=2;i<L.length;++i) // if (LT(L.r[i].key,L.r[i-1].key)) // { // L.r[0]=L.r[i]; // L.r[i]=L.r[i-1]; // for (j = i-2; LT(L.r[0].key,L.r[j].key);--j) // L.r[j+1]=L.r[j]; // L.r[j+1]=L.r[0]; // } //} void swap(int array[],int i,int j) { int temp=array[i]; array[i]=array[j]; array[j]=temp; } //插入排序 //最差情况下,直接插入排序的最大时间代价为θ(n²),最小时间代价为θ(n),平均时间代价为θ(n²)。 void InserSort(int array[],int n) { for (int i=1;i<n;++i) { for (int j=i;j>0;--j) { if (array[j]<array[j-1]) swap(array,j,j-1); else break; } } } //冒泡排序 //冒泡排序的最大时间代价,最小时间代价和平均时间代价均为θ(n²)。 void BubbleSort(int array[],int n) { for (int i=0;i<n-1;i++) { for (int j=n-1;j>i;--j) { if(array[j]<array[j-1]) swap(array,j,j-1); } } } // 选择排序的最大时间代价,最小时间代价和平均时间代价均为θ(n²)。选择排序不依赖于原始数组的输入顺序。 //选择排序 void SelectionSort(int array[],int n) { for (int i=0;i<n-1;++i) { int smallest=i; for(int j=i+1;j<n;++j) { if(array[smallest]>array[j]) smallest=j; } swap(array,i,smallest); } } //希尔排序 //增量为2的shell排序的时间代价可以达到θ(n的3/2次方),有的增量可以达到θ(n的7/6次方),很接近θ(n)。 void ShellSort(int array[],int n) { for(int delta=n/2;delta>0;delta/=2) for(int i=0;i<delta;++i) for(int j=i+delta;j<n;j+=delta) for(int k=j;k>0;k-=delta) if(array[k]<array[k-1]) swap(array,k,k-1); } //快速排序的最大时间代价为θ(n²),最小时间代价为θ(n*logn),平均时间代价为θ(n*logn)。 //快速排序 //构造轴点 int partition(int array[],int low,int high) { //以尾元素array[high]作为候选轴 int i=low-1; for (int j=low;j<high;++j)//遍历low到high-1的元素 { if(array[j]<array[high]) { ++i; swap(array,i,j); } } swap(array,high,(i+1)); return i+1; } void QuickSort(int array[],int low,int high) { if(low>high) return; int q=partition(array,low,high); QuickSort(array,low,q-1); QuickSort(array,q+1,high); } //归并排序 //归并排序的最大时间代价,最小时间代价和平均时间代价均为θ(n*logn)。归并排序不依赖于原始数组的有序程度。 //归并过程--将两个有序的数组合并成一个有序数组 void merge(int array[],int left,int middle,int right) { int *tempArray = new int[right-left+1]; int index1=left; int index2=middle+1; int i=0; while(index1<=middle&&index2<=right) { if (array[index1]<=array[index2]) tempArray[i++]=array[index1++]; else tempArray[i++]=array[index2++]; } while (index1<=middle) tempArray[i++]=array[index1++]; while (index2<=right) tempArray[i++]=array[index2++]; for(int j=0;j<i;++j) array[left+j]=tempArray[j]; delete[] tempArray; } //递归大法好 void MergeSort(int* array,int left,int right) { if(left>=right||array==NULL) return; //if(right-left<2) return ; int middle=(left+right)/2; MergeSort(array,left,middle); MergeSort(array,middle+1,right); merge(array,left,middle,right); } //堆排序 //堆排序的最大时间代价,最小时间代价和平均时间代价均为θ(n*logn)。堆排序和归并排序一样,不依赖于原始数组的有序程度。 //输入为要被排序的数组和根节点,数组a党组被维护的那部分的下表是low,high void MaxHeapify(int* a,int i,int low,int high) { int l=left(i); int r=right(i); int largest=0; if (l<=high&&a[l]>a[i]) largest=l; else largest=i; if(r<high && a[r]>a[largest]) largest=r; if(largest!=i) { swap(a,largest,i); MaxHeapify(a,largest,low,high); } } void BuildMaxHeap(int* a,int length) { for(int i=length/2-1;i>=0;--i) MaxHeapify(a,i,0,length-1); } void HeapSort(int a[],int length) { BuildMaxHeap(a,length); for(int i=length-1;i>=1;--i) { swap(a,0,i); MaxHeapify(a,0,0,i-1); } } //基数排序 //基数排序的时间复杂度为O (nlog(r)m),其中r为所采取的基数,而m为堆数,在某些时候,基数排序法的效率高于其它的比较性排序法。 //基数排序法是属于稳定性的排序。 /*计算关键字位数的最大值*/ int KeySize(int array[],int size) { int keyMax=0; for (int i=0;i<size;++i) { int temp=1; int n=10; while(array[i]/n) { temp++; n*=10; } keyMax=(temp>keyMax)?temp:keyMax; } return keyMax; } //void RadixSort(int array[],int size) //{ // int bucket[10][10]={0};//定义基数桶 // int order[10]={0};//保存每个基数桶之中的元素个数 // int keyMax=KeySize(array,size); // for(int n=1;keyMax>0;n*=10,keyMax--) // { // //将待排序的元素按关键值得大小依次放入基数桶中 // for (int i=0;i<size;i++) // { // int lsd=(array[i]/n)%10; // bucket[lsd][order[lsd]]=array[i]; // order[lsd]++; // } // //将基数桶中的元素重新串接起来 // int k=0; // for(int i=0;i<10;++i) // { // if (order[i]!=0) // { // for (int j=0;j<order[j];++j) // { // array[k]=bucket[i][j]; // k++; // } // order[i]=0; // } // } // // } // //} void RadixSort(int array[],int size) { int r=1; int tmp[10]; int count[10]; int keyMax=KeySize(array,size); for(int i=0;i<keyMax;i++) { for(int i=0;i<10;i++)//装桶之前要先清桶 count[i]=0; for(i=0;i<size;i++) //记录每个桶的记录数 { int k=array[i]/r; int q=k%10; count[q]++; } for(i=1;i<10;i++)//计算位置 { count[i]+=count[i-1]; //cout<<count[i]<<" "; } for(int j=size-1;j>=0;j--) { int p=array[j]/r; int s=p%10; tmp[count[s]-1]=array[j]; count[s]--; } for(i=0;i<size;i++) array[i]=tmp[i]; r=r*10; } } //归并,快速和基数排序最常考 int main() { int array[10]={9,1,2,7,15,5,8,3,6,4}; //InserSort(array,10);//插入排序 //BubbleSort(array,10);//冒泡排序 //SelectionSort(array,10);//选择排序 //ShellSort(array,10);//希尔排序(属于插入排序) //QuickSort(array,0,9);//快速排序 //MergeSort(array,0,9);//归并排序 //HeapSort(array,10);//堆排序(属于选择排序) RadixSort(array,10);//未测试成功,待改进 for (int i=0;i<10;++i ) cout<<array[i]<<" "; cout<<endl; system("pause"); return 0; }