栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

排序算法:shell 希尔排序

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

排序算法:shell 希尔排序

希尔排序

  • 此算法建立在其他排序算法上(插入、冒泡等),但依据希尔排序的特性使用插入排序会更加高效。
  • 首先,将要排序的数组,按照一定的增量分出子序列,我们对子序列利用插入排序算法排序。
  • 然后,增量=增量/2(自己按照实际情况设置增量),在按照增量分出子序列,对它们进行排序。
  • 如此往复,直到增量=1时,就像普通数组(但此时的数组比原数组更有序)那样进行最后一次插入排序(在有序性大的数组使用插入排序更好)后即可结束。
  • 增量可以看作子序列中各个节点的距离,以及子序列的个数。

图解

来自网上

代码模板

public void ShellSort() {
       int[] arr = new int[]{3, 4, 5, 2, 1, 7, -1, 9, 0};

       //增量
       int incre = arr.length / 2;
       while (incre != 0) {
           //根据增量分出子序列,遍历各个子序列,开始插入排序
           for (int i = 0; i < incre; i++) {
               //对子序列利用插入排序算法进行排序
               //编写该循环需注意每个子序列的第一个值的位置,以及同一个序列中各个节点的距离
               for (int j = i + incre; j < arr.length; j += incre) {
                   //编写该循环需注意同一个序列中各个节点的距离
                   for (int k = j - incre; k >= 0; k -= incre) {
                       if (arr[k] > arr[k + incre]) {
                           int tmp = arr[k];
                           arr[k] = arr[k + incre];
                           arr[k + incre] = tmp;
                       } else break;
                   }
               }
           }
           //增量每次除以2,增量为1且又进行过插入排序时,表示数组已经有序
           incre /= 2;
       }
       for (int i : arr) {
           System.out.println(i);
       }
   }

总结

希尔排序是插入排序的变种,这并不意味着希尔排序的效率一定比插入排序高。
在进行测试时,用到测试案例数据规模不够大,或者有序程度高,则可能运行效率反而比插入排序低。

  • 那么希尔排序的优点是什么呢?
    首先回顾以下希尔排序的流程,它会先将原数组分为一个个子序列,再将这些子序列进行排序。
    注意这些子序列中的各个节点距离随着数据规模增大而增大,因此子序列的排序,我们可以花费很少的代价将位于数组末尾的数小的值(假定构造升序数组)移动到前面。
    因此希尔排序的数值交换次数会比插入排序少很多。
  • 在上面所说的层面上来看:数据规模越大,其效率与插入排序相比更加优秀。但其并不稳定,依赖原数组的具体情况。

希 尔 排 序 : 空 间 复 杂 度 O ( 1 ) , 其 时 间 复 杂 度 需 要 看 你 增 量 怎 么 取 希尔排序 :空间复杂度O(1),其时间复杂度需要看你增量怎么取 希尔排序:空间复杂度O(1),其时间复杂度需要看你增量怎么取
那到底增量怎么取,希尔排序算法才能达到最优呢?

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/301293.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号