希尔排序
在我看来,是将数组序列从大化中,中化小的一种排序方式,每一个化简的过程也是利用了直接插入排序,将数组基本排序,对于基本排序也就是大致有一个从小到大的顺序,在对这个基本的序列进行排序,在基本的序列里有的序列可能已经按照顺序排好,所以会省去一些步骤,以此来对排序算法进行优化。
void Shell_Sort(SqList* L)
{
int i, j;
int increment = L->length;
do
{
increment = increment / 3 + 1; // 设置每层循环的增量值
for (i = increment+1;i<=L->length;i++)
{
// 按每个增量的值,依次向后遍历
if (L->Array[i] < L->Array[i - increment])
{
// 比较增量下的两个值的大小,是否交换
L->Array[0] = L->Array[i]; // 这里用Array[0]作为中间两来交换两个数
for (j = i-increment; j > 0 && L->Array[0] < L->Array[j]; j-=increment)
// 这里的条件是用来结束每一个增量最后的位置
L->Array[j + increment] = L->Array[j];
L->Array[j + increment] = L->Array[0]; // 插入位置
}
}
} while (increment > 1); // 增量为1时结束排序
}
代码有点绕,所以让我们用图片的形式分析过程。
首先我们对最大增量时进行遍历,每一步都是先比较大小,在判断是否交换:
通过最大增量遍历后的序列,我们在其基础上进行增量递减的遍历:
再后来就是增量为2,增量为1,直至结束排序,得到一个从小到大的序列。
希尔排序的关键并不是随便分组后各自排序,而是将相隔某个增量的记录组成一个子序列,实现跳跃式的移动,使得排序的效率提高。—— 大话数据结构
以上便是我理解的希尔排序算法,可能与实际有部分偏差,还请多多指教。