1.折半插入排序
因为折半查找比直接查找更快,所以当需要排序的数字越多时,折半插入排序相较于直接插入排序效率更高。
2.算法思想
采用折半查找招待待排序元素的插入位置
3.代码实现
#include <stdio.h>
void display(int arr[],int size)
{
for(int i=1;i<size;i++)
printf("%d ",arr[i]);
printf("\n");
}
void BInsertSort(int arr[],int size)
{
int i,j,low,high,mid;
for(i=2;i<size;i++)
{
low=1;
high=i-1;
arr[0]=arr[i];
while(low<=high)
{
mid=(low+high)/2;
if(arr[mid]>arr[0])
high=mid-1;
else
low=mid+1;
} //high+1就是插入位置
for(j=i-1;j>=high+1;j--)
arr[j+1]=arr[j];
arr[high+1]=arr[0];
}
}
int main()
{
int arr[]={0,5,4,3,2,1};
int size=sizeof(arr)/sizeof(arr[0]);
display(arr,size);
BInsertSort(arr,size);
display(arr,size);
return 0;
}
4.运行结果
5.分析
该段代码中需要注意的有以下几点:
1.数组arr中的第一个元素是0,作为哨兵使用,不存放具体数据。
2.对于插入位置为high+1是为什么呢?首先对于while循环中,最后一次循环的情况是low=high,此时low,high,mid三个指向同一个位置,当arr[mid]>arr[0]时,high的值会减1,此时需要插入的值比arr[mid]小,所以需要将arr[mid]向后移动一个位置,所以high+1就是要插入的位置;当arr[mid]<=arr[0]时,low的值会加1,此时arr[mid]小于或等于需要插入的值,即需要插入的值要放在arr[mid]后面,即hight+1的位置,综上两种情况,我们会发现插入位置还可以是low。
3.该算法是稳定的,判断稳定的条件是,出现相同的数字时,其排序的相对位置和原来一样,该代码中出现相同元素的情况为while循环中的else情况,即arr[mid]<=arr[0],此时要插入的元素依然会插入到arr[mid]的后面,所以相对位置没有改变,即是稳定的。