文章目錄
希爾排序
#引用書籍以及地址
Solving with Algorithms and Data Structures
原文中有線上調試的功能,很好用
簡要說明:
希爾排序,有時也叫做“最小增量排序”,通過把原始的序列分解成幾個子序列來提高效率,其中每個小序列使用的都是插入排序。怎麼樣劃分這些子序列是希爾排序的關鍵。希爾排序不是直接把整個序列直接分割成連續的子序列,而是用了一個增量i,有時也叫做gap(間隔),通過選擇i劃分的list組成子序列。
請參見圖6。整個list有9個元素,如果我們使用3為增量,就會有3個子list,每個子list可以使用插入排序。所有子列表完成排序後,我們就可以得到圖7 。儘管結果並沒有完全排序,但發生了一些很有意思的事情。通過對子序列的排序,我們把這些元素放到離最終排序結果很近的地方。
圖6
圖7
圖8顯示了使用一個增量的最插入排序,換句話說就是標準的插入排序。注意通過前面的子list 的排序,我們現在已經減少了整個排序
的總操作次數。最多隻要4次移位就可以完成整個過程。
圖8
圖9
前面我們說過,怎樣去選擇排序分割的增量是希爾排序的獨特的特性。範例程式碼中我們就使用了不同的增量。這次我們開始用的是n/2個的子序列。然後,n/4個子序列。最後,整個list最後經過出一次基本的插入排序。圖9就是我們使用這種增量的例子。
下面shellSort函數的調用顯示了每次增量後的部分排序,在最後的插入排序之前從1個增量開始排序。
代碼
#utf8.py#python2.7 sellSort.pydef shellSort(alist): sublistcount = len(alist)//2 #計算取子列表的增量 第一次是4 ex:alist[0] alist[4] alist[8]為一個子組 while sublistcount > 0: #第二次sublistcount=2 ex:alist[0] alist[2] alist[4] alist[6] alist[8]為一個子組 for startposition in range(sublistcount): gapInsertionSort(alist,startposition,sublistcount) print("After increments of size",sublistcount, "The list is",alist) sublistcount = sublistcount // 2def gapInsertionSort(alist,start,gap): ''' 對子組進行插入排序 ''' for i in range(start+gap,len(alist),gap): currentvalue = alist[i] position = i while position>=gap and alist[position-gap]>currentvalue: alist[position]=alist[position-gap] position = position-gap alist[position]=currentvaluealist = [54,26,93,17,77,31,44,55,20] #將要排序列表 shellSort(alist) #調用排序print(alist)