希尔排序 C语言

2023-07-28 20:13:13 浏览数 (2)

碎碎念念

希尔排序是插入排序的一种,是直接插入排序的改进版。

我们首先来看直接插入排序,其基本思路是,一般先孤立这堆数字的第一个数,那么它自己一个就是有序了,再拿后面的数和它比较,找到大小位置合适的插进去,完了之后这一小堆还是有序的,再拿后面的来和前面的比较,找到合适的位置插进去,直到全部插完。

直接插入排序的优势

从直接插入排序的思想可以知道,如果这堆数原本就比较有序了,那么直接插入排序是非常高效的,因为交换次数会少很多。

直接插入排序的劣势

但有一种情况是,假设是从小到大排序,前面已经排好了一万个有序数,到这10001个数的时候,恰好它是最小的那一个,那么就要和前面的数全部交换一次,,这就出现了交换距离过长的问题,这是我们不希望看到的。

希尔排序

基于直接插入排序的这两个特点,我们引入了它的升级版——希尔排序。

希尔排序又被称作缩小增量排序。

为了解决直接插入排序交换距离过长问题,我们设想如果能让这一堆待排序的数中比较小的数在一边,比较大的数在另一边,那么发生交换的时候就不用跨过千山万水了。

也就是说,我们要先对这一堆数进行预排序,具体操作是,先选定一个数interval(一般是数字的总数的一半)作为第一增量,然后把间隔为interval的数作为一个小组,对这个小组进行直接插入排序,然后缩小interval(一般是让interval减半)作为第二增量,继续分小组进行直接插入排序,以此类推,操作下去,到interval等于1的时候,小组间间隔为1,也就是对全部元素进行直接插入排序,但整个时候,这一堆数已经相对有序了,直接插入排序这个时候就十分高效了。

代码

代码语言:javascript复制
#include<stdio.h>
void insert(int a[],int n) 
{
	int i,temp,j,interval=n/2;
	while(interval>0)//和直接插入相比,就是i和j的变化以interval为单位了。 
	{
		for(i=interval;i<n;i=i interval)//划分小组。 
		for(j=i;j>0;j=j-interval)//小组内进行直接插入排序。 
		if(a[j]<a[j-interval]) 
		{
			temp=a[j];
			a[j]=a[j-interval];
			a[j-interval]=temp;
		}
		interval=interval/2;	
	}
} 
int main()
{
	int a[10]={7,3,1,6,2,0,5,8,4,9};
	insert(a,10);
	for(int i=0;i<10;i  )
	printf("%d ",a[i]);
}

链接——直接插入排序

https://blog.csdn.net/weixin_62264287/article/details/122895216?spm=1001.2014.3001.5501

0 人点赞