1. 程式人生 > >排序算法之希爾排序

排序算法之希爾排序

java 排序算法 希爾排序


希爾排序

先將整個待排序的序列分割成若幹個子序列分別進行直接插入排序,當整個序列的元素“基本有序”時,再對全體進行一次直接插入排序。

需要註意的是,子序列的構成不是簡單的“逐段分割”,而是將相隔某個“增量”的記錄組成一個子序列,如第一趟增量為5,第二趟增量可以為3等等。

這個增量習慣上用字母h來表示這個增量, 常用的h序列由Knuth提出,該序列從1開始,通過如下公式產生:h = 3 * h +1。

例如下述過程:

技術分享圖片

希爾排序穩定性

希爾排序是不穩定的算法,它滿足穩定算法的定義。對於相同的兩個數,可能由於分在不同的組中而導致它們的順序發生變化。

希爾排序時間復雜度

希爾排序的時間復雜度與增量(即步長gap)的選取有關。如,當增量為1時,希爾排序退化為直接插入排序,此時的時間復雜度為0(N),而Hibbard增量的希爾排序的時間復雜度為0(N^3/2)。


Java實現

package acm;
/*希爾排序
 * 2017.11.22
 * 希爾排序算法減小數據項的間隔再進行排序,依次進行下去,進行這些排序時的數據項
 *  之間的間隔被稱為增量,習慣上用字母h來表示這個增量。
 * 常用的h序列由Knuth提出,該序列從1開始,通過如下公式產生:h = 3 * h +1
*/
public class ShellSort {
     
     static void shellSort(int[] ary){
          int h = 1;
          //計算h可取的最大值
          while(h <= ary.length/3){
              h = 3*h+1;
          }         
          while(h>0){
              for(int i=h;i<ary.length;i+=h){
                   if(ary[i]<ary[i-h]){
                        int temp = ary[i];
                        int j = i-h;
                        while(j>=0 && ary[j]>temp){
                             ary[j+h] = ary[j];
                             j-=h;
                        }
                        ary[j+h] = temp;
                        for(int ele:ary){
                             System.out.print(ele+",");
                        }
                        System.out.println("");//換行
                   }    
              }
              h = (h-1)/3;
          }
          
     }
     public static void main(String[] args){
          int[] ary = new int[]{49,38,65,97,76,13,27,49,55,4};
          shellSort(ary);
     }
}



本文出自 “衛莨” 博客,請務必保留此出處http://acevi.blog.51cto.com/13261784/1983982

排序算法之希爾排序