一、希尔排序
1.概念
希尔排序(Shell Sort)是插入排序的一种,它是针对直接插入排序算法的改进。
希尔排序又称缩小增量排序,因 DL.Shell 于 1959 年提出而得名。
它通过比较相距一定间隔的元素来进行,各趟比较所用的距离随着算法的进行而减小,直到只比较相邻元素的最后一趟排序为止。
2.演示
选择增量 gap=length/2,缩小增量以 gap = gap/2 的方式
(1)初始增量第一趟 gap = length/2 = 4
(2)第二趟,增量缩小为 2
(3)第三趟,增量缩小为 1,得到最终排序结果
3.代码(交换法)
public static void shellSort(int[] array){
int temp = 0;
for (int gap = array.length/2;gap>0;gap/=2){
for (int i = gap; i < array.length; i++) {
for (int j = i-gap; j >=0; j -= gap) {
if (array[j]>array[j+gap]){
temp = array[j];
array[j] = array[j+gap];
array[j+gap] = temp;
}
}
}
}
}
二、优化
(1)对增量序列优化:使用更加复杂的方式。
上面使用2的倍数
(2)对每一趟的插入排序进行优化
使用移位法优化,if 判断
public static void shellSort2(int[] arr) {
int temp = 0;
for (int group = arr.length / 2; group > 0; group /= 2) {
//对每一次遍历进行插入排序
for (int i = group; i < arr.length; i++) {
temp = arr[i];
int j = i;
if (arr[j] < arr[j - group]) {
while (j - group >= 0 && temp < arr[j - group]) {
arr[j] = arr[j - group];
j -= group;
}
arr[j] = temp;
}
}
}
}
2.复杂度分析
由于希尔排序的复杂度跟增量序列的选择有关;
目前最好的平均时间复杂度为O(n^1.3);
3.希尔排序适用的情况
中等大小规模表现良好,对规模非常大的数据排序不是最优选择。
4.稳定性分析
由于多次插入排序,我们知道一次插入排序是稳定的,不会改变相同元素的相对顺序,但在不同的插入排序过程中,相同的元素可能在各自的插入排序中移动,最后其稳定性就会被打乱,所以shell排序是不稳定的。