数据结构——希尔排序

一、前言

直接插入存在优化:可以通过对已排序好的序列,通过二分的方法,来找到待插入值的合适位置。

二分:

核心思路:每次砍掉一半范围,快速缩小答案区间,效率极高。

二、希尔排序(缩小增量排序)-》对直接插入排序的优化

1.核心:用到了缩小增量数组

2.直接插入排序的特点:

(1)数据也有序,整体排序效率越高。

(2)当n比较小的时候,n^2也不会很大-》时间复杂度 直接插入排序最理想的待排序序列是已经排序好的序列,所以时间复杂度就是O(n) 最糟糕的状态就是待排序序列是完全倒序,所以时间复杂度就是O(n^2)。

3.希尔排序的逻辑:

先将整个待排记录序列分割成为若干子序列分别进行直接插入排序,待整个序列中记录"基本有序"时,在对全体记录进行一次直接插入排序。

跳着分组:

①第一次以增量为5为例,每个颜色对应的数据是一组。然后对这每一组单独进行直接插入排序。

不用排 10 21 50 本身有序。

按照刚刚方法完全排序完的序列:

②第二次以增量3为例,每个颜色对应的数据是一组。然后对这每一组单独进行直接插入排序。

以增量为3排序完的序列完全排序完的结果是

③第三次按照增量1排序,每个颜色对应的数据是一组。然后对这每一组单独进行直接插入排序。

以增量为1排序完的序列完全排序完的结果是

此时,最终只要按照增量1处理之后,会完全有序

3.缩小增量数组的取值好坏和希尔排序的时间复杂度直接相关,但又没有一个最优解。

但他有一些规则:

(1)取值从大到小

(2)取值尽量互素

(3)最后一个增量必须是1

4.希尔排序的特点:子序列的构成不是简单的"逐段分割",而是将相隔某个"增量"的记录组成一个子序列。

5.时间复杂度:

希尔排序的分析是个复杂的问题,因为它的时间是所取"增量"序列的函数,这涉及一些数学上尚未解决的难题。通俗的来说他的时间复杂度是动态变化的,到目前为止尚未有人求得一种最好的增量序列。增量序列可以有各种取法,但需注意:应使增量序列中的值没有除1之外的其他公因子也就是说他是素数,并且最后一个增量值必须等于1.

三、代码实现

方法一:以增量3为例

此时我们先处理红色组,再处理绿色组,最后处理蓝色组

此时有效值的处理顺序为:

红1->红2->红3->红4->红5->绿1->绿2->绿3->绿4->绿5->蓝1->蓝2->蓝3->蓝4->蓝5

时间复杂度是O(n^3).

方法二:

不再处理完一个组,再处理下一个组,而是每一个组一次只处理一个值,然后轮换,直到所有的值处理完毕。

全部此时有效值的处理顺序为:

红2->绿2->蓝2->红3->绿3->蓝3->红4->绿4->蓝4->红5->绿5->蓝5

代码实现:

cs 复制代码
void Shell(int arr[], int len, int gap_val) {
	//此时增量为5;
	//需要将每一个执行插入排序
	for (int i = gap_val;i < len;i++) {//此时i控制的需要往前插入的待排序值 gap_val前面的值都是每一组的第一个元素,第一个元素不用排
		int tmp = arr[i];
		int j = i - gap_val;
		for (;j >= 0;j -= gap_val) {
			if (arr[j] > tmp) {
				arr[j + gap_val] = arr[j];
			}
			else {
				break;//遇到了不大于我的值,停下来把值放回去
			}
		}
		//越界了,停下来,把值放回去
		arr[j + gap_val] = tmp;
	}
}
void Shell_Sort(int arr[], int len) {
	int Gap[] = { 5,3,1 };
	int len_Gap = sizeof(Gap) / sizeof(Gap[0]);
	for (int i = 0;i < len_Gap;i++) {//趟数
		Shell(arr,len,Gap[i]);
	}
}
相关推荐
三克的油1 小时前
数据结构-4
数据结构
0566463 小时前
Python康复训练——数据结构
数据结构·windows·python
冻柠檬飞冰走茶3 小时前
PTA基础编程题目集 7-27 冒泡法排序(C语言实现)
c语言·开发语言·数据结构·算法
noipp6 小时前
推荐题目:洛谷 P5843 [SCOI2012] Blinker 的噩梦
c语言·数据结构·c++·算法·游戏·洛谷·luogu
冻柠檬飞冰走茶7 小时前
PTA基础编程题目集 7-20 打印九九口诀表(C语言实现)
c语言·开发语言·数据结构·算法
红叶舞7 小时前
基于线段树的数据结构
数据结构·python·算法
断点之下8 小时前
从“理扑克牌”到“分组优化”——直接插入排序与希尔排序详解
数据结构·算法·排序算法
起个破名想半天了8 小时前
算法与数据结构之DFS深度优先遍历
数据结构·算法·深度优先
鱼子星_9 小时前
【C++】深入剖析list:list及其双向迭代器实现
开发语言·数据结构·c++·笔记·stl·list
江屿风9 小时前
【C++笔记】【二叉搜索树】流食般投喂
开发语言·数据结构·c++·笔记