1. 程式人生 > >《大話資料結構》程式碼實現——第九章 排序

《大話資料結構》程式碼實現——第九章 排序

排序方法總體分為三類:

方法類別 低階 高階
插入排序 直接插入排序 希爾排序
選擇排序 簡單選擇排序 堆排序
交換排序 氣泡排序 快速排序
歸併排序 歸併排序

在此對每個排序方法做下總結以及實現:

一、插入類排序

1. 直接插入排序:將一個記錄插入到已經排好序的有序表中

def zhijiecharu(list):
    if not list:
        return false
    for i in range(1, len(list)):
        tmp = list[i]
        j = i-1
        if tmp < list[j]:
            while(list[j] > tmp and j >= 0):
                list[j+1] = list[j]
                j -= 1
            list[j+1] = tmp
    return list
if __name__ == '__main__':
    array = [49, 38, 65, 97, 76, 13, 27, 49, 55, 4]
    print(zhijiecharu(array))

2. 希爾排序:為了使整個序列變得基本有序,在直接插入基礎上,增加了Increment這個變數,先跳著進行一次直接插入排序,這個跳的步幅越來越小,最後一次就是1.

寫程式碼時出錯的點:

(1)temp搞不清楚是給新來的數還是下標減increment的數

(2)while裡面經常忘了寫and j>=0這個條件


def shell_sorted(list):
    if not list:
        print(False)
    incremnt = len(list)
    while incremnt > 1:
        incremnt = incremnt // 3 + 1
        # print(incremnt)
        for i in range(incremnt, len(list)):
            temp = list[i]
            j = i - incremnt
            if list[j] > temp:
                while(list[j] > temp and j >= 0):
                    list[j+incremnt] = list[j]
                    j -= incremnt
                list[j+incremnt] = temp
    return list

if __name__ == '__main__':
    array = [49, 38, 65, 97, 76, 13, 27, 49, 55, 4]
    print(shell_sorted(array))

二、選擇排序類

1. 簡單選擇排序:在當前下標以後,選擇最小的數,和當前下標的數作比較並且交換


def easy_select(list):
    if not list:
        return False
    for i in range(len(list)):
        min_ind = i
        min_key = list[i]
        for j in range(i+1,len(list)):
            if list[j] < min_key:
                min_key = list[j]
                min_ind = j
        if i!=min_ind:
            temp = list[i]
            list[i] = min_key
            list[min_ind] = temp
    return list

if __name__ == '__main__':
    array = [49, 38, 65, 97, 76, 13, 27, 49, 55, 4]
    print(easy_select(array))

2. 堆排序:先將整個序列排成大頂堆,將堆頂元素與序列最後一個元素互換,再對前n-1個數字排成大頂堆。

寫程式碼時出錯的點:

(1) python中下標不能直接乘以2,應該2*(i+1)-1

(2)while的最後一句有點不太清楚是寫外面還是寫裡面

def swap(list, i, j):
    temp = list[i]
    list[i] = list[j]
    list[j] = temp
    return list

def get_heap(list, start_ind, end_ind):
    j = 2 * (start_ind + 1) - 1
    while(j <= end_ind ):
        temp = list[start_ind]
        if (j+1)<=end_ind and list[j] < list[j+1]:
            j +=1
        if list[j] <= temp:
            break
        else:
            list[start_ind] = list[j]
            list[j] = temp
            start_ind = j
            j = 2*(j+1)-1
    # list[(j+1)//2-1] = temp
    print(list)

def heap_sort(list):
    if not list:
        return False
    for i in range(len(list)//2-1,-1,-1):
        m = len(list)-1
        get_heap(list, i, m)
    for j in range(len(list)-1,-1,-1):
        swap(list, 0, j)
        get_heap(list, 0, j-1)
    return list



if __name__ == '__main__':
    array = [49, 38, 65, 97, 76, 13, 27, 49, 55, 4]
    array2 = [5,1,9,3,7,4,8,6,2]
    # print([i for i in range(3,-1,-1)])
    print(heap_sort(array2))

三、交換類排序

1. 氣泡排序:相鄰兩個逐個對比

def maopao(list):
    if not list:
        return False
    for i in range(len(list) - 1):
        for j in range(len(list)-2, i-1, -1):
            if list[j] > list[j+1]:
                temp = list[j]
                list[j] = list[j+1]
                list[j+1] = temp
    return list
if __name__ == '__main__':
    array = [9,1,5,8,3,7,4,6,2]
    print(maopao(array))

2. 快速排序:首先選定一個pivotkey並獲取其在待排序列中的座標Pivot,保證pivot左邊所有數字均小於pivotkey,右邊所有數字均大;根據pivot位置,將待排序列分成左右兩個子序列,再對兩個子序列進行遞迴來排序。(排序的交換操作實際上在獲取pivot的過程中進行)


def quick_sort(list):
    if not list:
        return False
    qsort(list, 0, len(list)-1)
    return list

def get_pivot_ind(list, low, high):
    # get pivot
    mid = (low + high)//2
    if list[low] > list[high]:
        temp = list[low]
        list[low] = list[high]
        list[high] = temp
    if list[mid] > list[high]:
        temp = list[mid]
        list[mid] = list[high]
        list[high] = temp
    if list[low] < list[mid]:
        list[mid],list[low] = list[low],list[mid]
        # temp = list[mid]
        # list[mid] = list[low]
        # list[low] = temp
    temp = list[low]
    while(low < high):
        while(low < high and list[high] > temp):
            high -= 1
        list[low] = list[high]
        while(low < high and list[low] < temp):
            low += 1
        list[high] = list[low]
    list[low] = temp
    return low

def qsort(list, low, high):

    while (low < high):
        pivotind = get_pivot_ind(list, low, high)
        qsort(list, low, pivotind-1)
        low = pivotind + 1
    return list

if __name__ == '__main__':
    array = [9,1,5,8,3,7,4,6,2]
    print(quick_sort(array))

四、歸併類排序