1.直接插入排序
//思想:从无到有,数组一直保持有序递增,新来的元素P与数值R从末到首比较,若P小于数组数值,则将数组值后移,为P的插入预留空间
//R从R[1]开始储存,最坏情况下时间R中元素递增,时间复杂度为O(n^2),空间复杂度为O(1)
void InsertSort(int R[],int n)
{
int i,j;
int temp;
for(i=2;i<=n;i++){
temp=R[i];
j=i-1;
while(j>=1&&temp<R[j]){
R[j+1]=R[j];
j--;
}
R[j+1]=temp;
}
}
//思想:从无到有,数组一直保持有序递增,新来的元素P与数值R从末到首比较,若P小于数组数值,则将数组值后移,为P的插入预留空间
2.折半插入排序
//折半查找第一个比num大的值的前一位的下标
int BinarySearch(int R[],int low,int high,int num)
{
int mid=(low+high)/2;
//小于中间值,在低区域,若在这里加用num<=R[mid],则会返回第一个小于R[mid]的数的下标,,若没有则返回0
// num<R[mid],则会返回第一个大与R[mid]的数的前一个数的下标,若没有则返回0
if(num<R[mid]){
high=mid-1;
if(low>high)
return high;
}else{
low=mid+1;
if(low>high)
return high;
}
return BinarySearch(R,low,high,num);
}
//R从R[1]开始储存,最坏情况下时间R中元素递增,时间复杂度为O(n^2)
void InsertSort(int R[],int n)
{
int i,j;
int temp;
for(i=2;i<=n;i++){
temp=R[i];
j=i-1;
int low=BinarySearch(R,1,i,R[i]);
while(j>low){
R[j+1]=R[j];
j--;
}
R[j+1]=temp;
}
}
3.希尔排序(缩小增量排序)
//R从R[1]开始储存,最坏情况下时间R中元素递增,时间复杂度为O(n^2),空间复杂度为O(1)
//以下为对直接插入排序进行改造,引入起始下标,以及interval为最小位移,对应增量
void InsertSort(int R[],int n,int begin,int interval)
{
int i,j;
int temp;
for(i=begin+interval;i<=n;i+=interval){
temp=R[i];
j=i-interval;
while(j>=1&&temp<R[j]){
R[j+interval]=R[j];
j-=interval;
}
R[j+interval]=temp;
}
}
//希尔排序(缩小增量排序)Diminishing Increment, 这里简称DI, 如int DI[3]={5,3,1};
void ShellSort(int R[],int n,int DI[],int num){
for(int i=0;i<num;i++){
for(int j=0;j<DI[i];j++)
InsertSort(R,n,1+j,DI[i]);
}
}