希尔排序(Shell's Sort)是
插入排序的一种又称“缩小增量排序”(Diminishing Increment Sort),是直接插入排序算法的一种更高效的改进版本。希尔排序是非稳定排序算法。该方法因D.L.Shell于1959年提出而得名。
希尔排序是把记录按下标的一定增量分组,对每组使用直接插入排序算法排序;随着增量逐渐减少,每组包含的关键词越来越多,当增量减至1时,整个文件恰被分成一组,算法便终止。
算法描述
- 选择一个增量序列t1,t2,…,tk,其中ti>tj,tk=1;
- 按增量序列个数k,对序列进行k 趟排序;
- 每趟排序,根据对应的增量ti,将待排序列分割成若干长度为m 的子序列,分别对各子表进行直接插入排序。仅增量因子为1 时,整个序列作为一个表来处理,表长度即为整个序列的长度。
算法的时间复杂度
最好时间复杂度(同插入排序):O(n)
最坏时间复杂度(同插入排序):O(n^2)
平均时间复杂度:O(n^1.3)
代码实现
#include <iostream>
using namespace std;
void print(int arr[], int len)
{
for(int i = 0; i != len; ++i)
cout << arr[i] << " ";
cout << endl;
}
void insertionSort(int arr[], int len, int dt)
{
for(int i = dt; i != len; i+=dt )
{
int current = arr[i];
int j = i - 1; // 前一个
while(j != -1 && arr[i] < arr[j])
{
arr[j + 1] = arr[j];
--j;
}
arr[j + 1] = current;
}
cout << "增量为" << dt << ":" << endl;
print(arr,len);
}
void shellSort(int arr[], int len, int dt)
{
while(dt){
insertionSort(arr,len, dt);
dt /= 2;
}
}
int main()
{
int arr[] = {0,3,4,2,7,14,6,5,4,10};
cout << "原始数据:" << endl;
print(arr, 10);
shellSort(arr, 10, 5);
return 0;
}
运行结果
原始数据:
0 3 4 2 7 14 6 5 4 10
增量为5:
0 3 4 2 7 14 6 5 4 10
增量为2:
0 3 4 2 4 7 6 14 5 10
增量为1:
0 3 2 4 4 6 7 5 10 14