希尔排序
希尔排序是对插入排序的改进
基于以下两点性质:
- 插入排序对于几乎已经排好序的数据操作时,效率高
- 但插入排序一般来说都是低效的,因为插入排序每次只能将数据移动一位
定义增量gap,即序列被分成gap组
注意这里的分组元素不是连续的
盗个图
对每组分别进行直接插入排序,然后缩小增量
它减少了比较并交换的次数
思想是:
- 先将待排序列分割为若干子序列分别进行直接插入排序
- 带整个序列“基本有序”时,再对整个序列进行直接插入排序
算法执行过程大概数,
- 首选确定一个初始增量gap
- 然后从gap位置向后操作,对于每一个元素
- 看他与同组前一个元素大小比较,如果小于就交换
那么问题来了,只往钱比,能确定后面就没有了吗?换句话说,能确定gap就是…
确实没法保证后面,但是它会遍历到后面的,找前面只相当于直接插入向前找位置的操作
而且gap+1能保证是各组第一个元素的后一个
template<typename T>
void shell_sort(vector<T>& nums) {
int n = nums.size(),h=1;
// 初始化细节
while (h < 3 / n) h = 3 * h + 1;
while (h >= 1) {
for (int i = h; i < n; i++)
// 改这里nums[j] < nums[j - h]大于小于就可以变为降序
for (int j = i; j - h >= 0 && nums[j] < nums[j - h]; j -= h)
swap(nums[j], nums[j - h]);
h /= 3;
}
}