十個(gè)必知的排序算法|Python實(shí)例系列[1]

實(shí)例內(nèi)容:

十個(gè)必知的排序算法具體代碼,并簡略的得知每種算法對(duì)于不同長度數(shù)列的排序時(shí)間

十大排序:

1.冒泡排序2.選擇排序3.插入排序4.希爾排序5.歸并排序6.快速排序7.堆排序8.計(jì)數(shù)排序9.桶排序10.基數(shù)排序

代碼演示視頻

完整代碼和注釋如下

# -*- coding: UTF-8 -*-
#Space: https://github.com/Tri-x/exercise
#Space: https://space.bilibili.com/187492698
#Author: Trix
#Description: 十大經(jīng)典排序算法

#Python的排序算法用的是Tim Sort 一種源自歸并排序和插入排序的穩(wěn)定高效的排序算法 也許以后會(huì)單獨(dú)做一期視頻來介紹該算法
#也許以后會(huì)做一期視頻來介紹一些奇葩的排序算法 比如 睡眠排序、猴子排序、面條排序、珠排序

from random import randint#隨機(jī)整數(shù)
from time import process_time#計(jì)時(shí)

nums_lists=[[]for n in range(4)]#隨機(jī)創(chuàng)建四個(gè)無序數(shù)列 用來粗略地測(cè)試每種排序算法的用時(shí)
for n in range(500):#數(shù)列長度為500
    nums_lists[0].append(randint(-400,400))#隨機(jī)范圍(-400,400)
for n in range(1000):
    nums_lists[1].append(randint(-8000,8000))
for n in range(5001):
    nums_lists[2].append(randint(-2000,2000))
for n in range(10000):
    nums_lists[3].append(randint(-9000,9000))
#由于創(chuàng)建的隨機(jī)數(shù)列太長,就不打印排序前和排序后的結(jié)果了


def bubble_sort(num_list):#冒泡排序 該算法名字的由來是因?yàn)樵叫〉闹禃?huì)慢慢"浮"到數(shù)列的頂端
    #循環(huán)遍歷數(shù)列,一次比較兩個(gè)相鄰的值,如果后者值大于前者值,就把他們的位置互相交換
    for n in range(len(num_list)-1):#因?yàn)樽詈笠淮我呀?jīng)順序正確了所以循環(huán)次數(shù)-1
        for m in range(len(num_list)-1-n):
            #循環(huán)每結(jié)束一次 這一次循環(huán)中最大的值會(huì)移動(dòng)到上一次循環(huán)中最大值的前一位 數(shù)列中后面的值已經(jīng)有序 所以次數(shù)-n
            if num_list[m]>num_list[m+1]:#大小比較
                num_list[m+1],num_list[m]=num_list[m],num_list[m+1]#位置交換
    return num_list


def select_sort(num_list):#選擇排序 選擇最小值
    #每次循環(huán)在數(shù)列中找到最小值,放到上一次循環(huán)找到的最小值的后一位,第一次放在首位
    for n in range(len(num_list)-1):#因?yàn)樽詈笠淮我呀?jīng)順序正確了所以循環(huán)次數(shù)-1
        min_index=n#設(shè)最小值為索引為n的值
        for m in range(n,len(num_list)):#n值前已完成排序
            if num_list[m]<num_list[min_index]:#最小值比較
                num_list[min_index],num_list[m]=num_list[m],num_list[min_index]#位置交換
    return num_list


def insert_sort(num_list):#插入排序 插入數(shù)值 此版本為插入排序最原始的版本
    #每次循環(huán)把索引為1的值到索引為第n次的值作為有序數(shù)列,把有序數(shù)列以外的每個(gè)值插入有序數(shù)列的正確位置
    for n in range(1,len(num_list)+1):#從第二個(gè)值開始
        for m in range(n):#每個(gè)值滾動(dòng)的范圍是其索引值
            if n<len(num_list):#防止n值超出數(shù)列長度
                if num_list[n]<=num_list[m]:#比較大小
                    num_list[n],num_list[m]=num_list[m],num_list[n]#位置交換
    return num_list


def shell_sort(num_list):#希爾排序 插入排序的改進(jìn)版 shell的音譯
    #把整個(gè)無序數(shù)列按步長值分組,對(duì)每組數(shù)列分別進(jìn)行插入排序,每次結(jié)束后減小步長,當(dāng)步長值減小到1時(shí)對(duì)整個(gè)數(shù)列插入排序
    gap=len(num_list)//2#gap為步長值 //為除法向下取值
    while gap>=1:#控制步長范圍
        #以下為插入排序的內(nèi)容 并對(duì)插入排序進(jìn)行了改進(jìn)
        for n in range(gap,len(num_list)):
            while (n-gap)>=0:#控制比較范圍
                if num_list[n]<num_list[n-gap]:#比較相鄰兩值大小
                    num_list[n],num_list[n-gap]=num_list[n-gap],num_list[n]#位置交換
                    n-=gap#把比較的兩個(gè)值的索引向前移
                else:#超出索引范圍后結(jié)束該循環(huán)
                    break
        gap//=2#每次結(jié)束時(shí)減小步長值
    return num_list

def merge_sort(num_list):#歸并排序 二分法 遞歸與合并
    #把無序數(shù)列遞歸地二分,直到只有兩個(gè)或一個(gè)值為一組時(shí),比較值的大小并排序,再返回這一組,
    #再遞歸地和其它組比較每個(gè)值的大小并排序,再返回排序的結(jié)果,再遞歸地返回成有序數(shù)列
    if len(num_list)<=1:#限制每組數(shù)列的最小長度
        return num_list
    middle=len(num_list)//2#二分值 //表示除法向下取整
    list_before=merge_sort(num_list[:middle])#數(shù)列前半部分為list_before 后半部分為list_after
    list_after=merge_sort(num_list[middle:])#這里最好自己舉例一個(gè)有2或3個(gè)值的數(shù)列,初次遇見遞歸思想可能比較難理解
    '''
    比如運(yùn)行merge_sort([3,2,1])
    [3,2,1]被分成了list_before=merge_sort([3])list_after=merge_sort([2,1])
        list_before=merge_sort([3]):merge_sort函數(shù)運(yùn)行時(shí),因?yàn)閇3]長度等于1了 所以直接返回[3] 即list_before=[3]
        list_after=merge_sort([2,1]):merge_sort函數(shù)運(yùn)行時(shí),list_after=merge_sort
        在list_after該函數(shù)內(nèi)部又二分成了list_before=merge_sort([2])list_after=merge_sort([1])
            與list_before=merge_sort([3])同理,在list_after該函數(shù)內(nèi)部中,list_before=[2],list_after=[1]
            接著在list_after該函數(shù)內(nèi)部中,執(zhí)行return merge_compare(list_before,list_after)
            也就是比較[2]和[1]的大小后排序并返回 結(jié)果也就是list_after=[1,2]
        再執(zhí)行return merge_compare(list_before,list_after)也就是比較[3]和[1,2]大小后排序并返回
        結(jié)果也就是return [1,2,3]
    最后返回總列表 其它數(shù)列以此類推
    '''
    return merge_compare(list_before,list_after)#返回list_before,list_after比較的結(jié)果

def merge_compare(list_before,list_after):#比較兩個(gè)列表中的每個(gè)值
    result_list=[]#結(jié)果列表
    before_index=after_index=0#前列表和后列表數(shù)值的索引起始值
    while before_index<len(list_before) and after_index<len(list_after):#限制索引值
        if list_before[before_index]<list_after[after_index]:#如果前列表的值小于后列表的值
            result_list.append(list_before[before_index])#就把該值添加到結(jié)果列表
            before_index+=1#結(jié)束后索引值+1
        elif list_after[after_index]<=list_before[before_index]:#如果后列表的值小于等于前列表的值
            result_list.append(list_after[after_index])#同理
            after_index+=1
    if before_index==len(list_before):#如果前列表的索引值已經(jīng)等于前列表長度了
        for n in list_after[after_index:]:#說明后列表的所有值大于前列表的最大值
            result_list.append(n)#因?yàn)楹罅斜碓谶f歸中已經(jīng)完成排序了 直接追加后列表
    elif after_index==len(list_after):#如果后列表的索引值已經(jīng)等于后列表長度了
        for n in list_before[before_index:]:#同理
            result_list.append(n)
    return result_list#返回排序結(jié)果


def quick_sort(num_list):#調(diào)用快速排序的遞歸函數(shù)
    quick_recursion(num_list,0,len(num_list)-1)#傳入數(shù)列,頭索引值和尾索引值

def quick_recursion(num_list,head_index,tail_index):#快速排序 遞歸思想 建議和歸并排序一樣舉例理解
    #從數(shù)列中任意挑選一個(gè)值(該值稱為基準(zhǔn)-Pivot),設(shè)置一個(gè)頭索引值和尾索引值,用來限定掃描范圍,頭索引值向尾索引值移動(dòng)
    #掃描每個(gè)值把所有小于基準(zhǔn)值的數(shù)移到其前,所有大于基準(zhǔn)的數(shù)移到其后(該步驟稱為分區(qū)-Partition),再在每個(gè)分區(qū)里遞歸以上步驟
    if head_index<tail_index:#限制索引值
        pivot_index=quick_partition(num_list,head_index,tail_index)#獲取基準(zhǔn)所在索引值 這一步同時(shí)也完成了分區(qū)
        quick_recursion(num_list,head_index,pivot_index-1)#分別在前后分區(qū)范圍內(nèi)進(jìn)行快速排序 因?yàn)榛鶞?zhǔn)值處于前分區(qū)結(jié)尾和后分區(qū)開頭
        quick_recursion(num_list,pivot_index+1,tail_index)#所以對(duì)于前分區(qū)的尾索引值-1 對(duì)于后分區(qū)的頭索引值+1
    return num_list

def quick_partition(num_list,head_index,tail_index):#比較大小并進(jìn)行分區(qū)
    pivot=num_list[tail_index]#為了方便 選取該分區(qū)的結(jié)尾值作為基準(zhǔn)-Pivot
    exchange_index=head_index-1#設(shè)置交換索引值 頭索引值-1能把幾種情況整合成一句代碼
    for n in range(head_index,tail_index):#在兩個(gè)索引值范圍內(nèi) 用基準(zhǔn)值來區(qū)分每個(gè)值
        if num_list[n]<pivot:#如果掃描值小于基準(zhǔn)值
            exchange_index+=1#控制交換索引值
            num_list[exchange_index],num_list[n]=num_list[n],num_list[exchange_index]#交換位置
    num_list[exchange_index+1],num_list[tail_index]=num_list[tail_index],num_list[exchange_index+1]#注意有個(gè)exchange_index+1
    '''
    比如quick_sort([1,4,5,6,3,4],0,5)
        在[1,4,5,6,3,4]中第一次分區(qū)時(shí)基準(zhǔn)值=4,exchange_index=-1
            n=0時(shí),掃描值1<基準(zhǔn)值,exchange_index+1=0,再執(zhí)行for循環(huán)時(shí)的下一行的交換位置的代碼 等效于掃描值1的位置不變
            n=1時(shí),掃描值4=基準(zhǔn)值,exchange_index不變,exchange_index仍為0
            n=2時(shí),掃描值5>基準(zhǔn)值,exchange_index不變,exchange_index仍為0
            n=3時(shí),掃描值6>基準(zhǔn)值,exchange_index不變,exchange_index仍為0
            n=4時(shí),掃描值3<基準(zhǔn)值,exchange_index+1=1,再執(zhí)行for循環(huán)時(shí)的下一行的交換位置的代碼 等效于掃描值4和掃描值3交換位置
        此時(shí)for循環(huán)結(jié)束,執(zhí)行for循環(huán)結(jié)束后的的下一行交換位置的代碼 等效于掃描值5和基準(zhǔn)值4交換位置
        第一次分區(qū)結(jié)束后我們得到了[1,3,4,6,4,5] partition函數(shù)返回了pivot_index=2
    接著在quick_sort函數(shù)內(nèi)部繼續(xù)運(yùn)行quick_sort([1,3,4,6,4,5],0,2-1)和quick_sort([1,3,4,6,4,5],2+1,5)
    即對(duì)于[1,3]和[6,4,5]進(jìn)行partition函數(shù),同理 不贅述
    對(duì)于整個(gè)數(shù)列遞歸partition結(jié)束后 排序也就完成 其它數(shù)列以此類推
    '''
    return exchange_index+1#返回基準(zhǔn)值所在的索引值


def heap_sort(num_list):#堆排序 完全二叉樹 遞歸
    #遞歸地把數(shù)列形成每個(gè)父節(jié)點(diǎn)>每個(gè)左右子節(jié)點(diǎn)的完全二叉樹
    #這樣每次構(gòu)建后索引[0]為最大值,在第n次結(jié)束,就把[0]和[-n]位置互換 在[0:-n-1]的范圍內(nèi)進(jìn)行下次的完全二叉樹構(gòu)建
    list_len=len(num_list)#獲取數(shù)列長度
    for n in range(list_len//2,-1,-1):
    #list_len//2為父節(jié)點(diǎn)索引的規(guī)律 //表示除法向下取整 n∈[list_len//2,-1),n∈Z range(start,stop,step) step為-1時(shí)為從后往前遍歷
        heapify(num_list,list_len,n)#數(shù)列完全二叉樹的初始化 構(gòu)建每個(gè)父節(jié)點(diǎn)>每個(gè)左右子節(jié)點(diǎn)的完全二叉樹
    for n in range(list_len-1,0,-1):#n∈[list_len-1,0),n∈Z
        num_list[0],num_list[n]=num_list[n],num_list[0]#對(duì)上一次構(gòu)建完成的二叉樹 首尾值互換
        list_len-=1#限定這一次構(gòu)造完全二叉樹的范圍
        heapify(num_list,list_len,0)#由于已經(jīng)初始化完成 可以直接從首項(xiàng)開始 在不包含上次最大值的范圍內(nèi)進(jìn)行構(gòu)造完全二叉樹
    return num_list

def heapify(num_list,list_len,parent_index):#構(gòu)建父節(jié)點(diǎn)>左右子節(jié)點(diǎn)的完全二叉樹
    #第n排有n^(n-1),從左到右填充數(shù)值,可以得到父節(jié)點(diǎn)索引和左右子節(jié)點(diǎn)索引的規(guī)律
    left_index=2*parent_index+1#對(duì)于每個(gè)父節(jié)點(diǎn)索引 左節(jié)點(diǎn)索引的規(guī)律
    right_index=left_index+1#對(duì)于每個(gè)父節(jié)點(diǎn)索引 右節(jié)點(diǎn)索引的規(guī)律
    max_index=parent_index#假設(shè)父節(jié)點(diǎn)比左右子節(jié)點(diǎn)值都大 默認(rèn)最大值的索引為父節(jié)點(diǎn)索引
    if left_index<list_len and num_list[left_index]>num_list[max_index]:#如果在列表范圍內(nèi) 左節(jié)點(diǎn)值>父節(jié)點(diǎn)值
        max_index=left_index#父節(jié)點(diǎn)和左節(jié)點(diǎn)的索引互換
    if right_index<list_len and num_list[right_index]>num_list[max_index]:#右節(jié)點(diǎn)同理
        max_index=right_index
    if max_index!=parent_index:#如果現(xiàn)在的父節(jié)點(diǎn)索引不等于一開始的假設(shè)的最大值的索引 說明父節(jié)點(diǎn)和它的某一節(jié)點(diǎn)需要互換索引值
        num_list[parent_index],num_list[max_index]=num_list[max_index],num_list[parent_index]
        heapify(num_list,list_len,max_index)#遞歸構(gòu)建整個(gè)數(shù)列的完全二叉樹


def count_sort(num_list):#計(jì)數(shù)排序 數(shù)數(shù)
    #找出數(shù)列中最大值和最小值 創(chuàng)建min~max這么多個(gè)0用來統(tǒng)計(jì)數(shù)列中每個(gè)值出現(xiàn)的次數(shù),再從最小值依次排放到最大值
    max_num=max(num_list)#找到最大值
    min_num=min(num_list)#找到最小值
    neg_list=[]#負(fù)數(shù)數(shù)列
    pos_list=[]#非負(fù)數(shù)數(shù)列
    for num in num_list:#對(duì)負(fù)數(shù)和非負(fù)數(shù)分別處理
        if num<0:
            neg_list.append(num)#向負(fù)數(shù)數(shù)列添加負(fù)數(shù)
        if num>=0:
            pos_list.append(num)#向非負(fù)數(shù)數(shù)列添加非負(fù)數(shù)
    if len(neg_list)!=0:#如果有負(fù)數(shù)
        neg_counts_list=[0 for n in range(min_num,0)]#創(chuàng)建最小值這么多個(gè)0來累計(jì)每個(gè)負(fù)數(shù)出現(xiàn)的次數(shù)
        for n in range(len(neg_list)):#對(duì)于負(fù)數(shù)數(shù)列中的每個(gè)值
            neg_counts_list[neg_list[n]]+=1
        neg_index=0#初始排序索引為0
        for n in range(-len(neg_counts_list),0):#對(duì)于計(jì)數(shù)列表中的每一項(xiàng)
            while neg_counts_list[n]>0:#不為0就說明有計(jì)數(shù) 為0說明沒有計(jì)數(shù)
                neg_list[neg_index]=n#依次排放數(shù)值
                neg_index+=1#每次排放后index+1
                neg_counts_list[n]-=1#每次排放后數(shù)值所對(duì)應(yīng)的計(jì)數(shù)-1
    if len(pos_list)!=0:#如果有非負(fù)數(shù)
        pos_counts_list=[0 for n in range(max_num+1)]#創(chuàng)建max+1這么多個(gè)0來累計(jì)每個(gè)非負(fù)數(shù)出現(xiàn)的次數(shù) 因?yàn)槭且悦總€(gè)值為索引 所以要max+1個(gè)0
        for n in range(len(pos_list)):#對(duì)于數(shù)列中的每個(gè)非負(fù)值
            pos_counts_list[pos_list[n]]+=1#計(jì)數(shù)列表索引和數(shù)列的值一一對(duì)應(yīng)
        pos_index=0#初始排序索引為0
        for n in range(len(pos_counts_list)):#對(duì)于計(jì)數(shù)列表中的每一項(xiàng)
            while pos_counts_list[n]>0:#不為0就說明有計(jì)數(shù) 為0說明沒有計(jì)數(shù)
                pos_list[pos_index]=n#依次排放數(shù)值
                pos_index+=1#每次排放后index+1
                pos_counts_list[n]-=1#每次排放后數(shù)值所對(duì)應(yīng)的計(jì)數(shù)-1
    result_list=neg_list+pos_list#負(fù)數(shù)數(shù)列和非負(fù)數(shù)數(shù)列結(jié)合
    return result_list


def bucket_sort(num_list):#桶排序 計(jì)數(shù)排序的改進(jìn)版
    #找出數(shù)列中最大值和最小值 創(chuàng)建min~max這么多個(gè)桶用來統(tǒng)計(jì)數(shù)列中每個(gè)值出現(xiàn)的次數(shù),再從第一個(gè)桶傾倒到最后一個(gè)桶
    bucket_list=[0 for n in range(max(num_list)-min(num_list)+1)]#創(chuàng)建min~max這么多個(gè)桶
    for n in range(len(num_list)):#對(duì)于當(dāng)前值
        bucket_list[num_list[n]-min(num_list)]+=1#添加到值對(duì)應(yīng)的桶內(nèi) 即對(duì)應(yīng)桶計(jì)數(shù)+1
    result_list=[]#結(jié)果列表
    for n in range(len(bucket_list)):#對(duì)于每個(gè)桶
        if bucket_list[n]!=0:#如果桶內(nèi)有數(shù)
            result_list+=[n+min(num_list)]*bucket_list[n]#直接把桶里的所有數(shù)倒出來
    return result_list


def radix_sort(num_list):#基數(shù)排序 比較位數(shù)上的值
    #比較每一位上的數(shù)字大小 當(dāng)每一位比較完成排序也就完成
    pos_list=[]#負(fù)數(shù)數(shù)列
    neg_list=[]#非負(fù)數(shù)數(shù)列
    for num in num_list:#對(duì)負(fù)數(shù)和非負(fù)數(shù)分別處理
        if num<0:
            neg_list.append(num)
        if num>=0:
            pos_list.append(num)

    if len(neg_list)!=0:#如果有負(fù)數(shù)
        neg_num_digit=0#初始位數(shù)
        while neg_num_digit<len(str(min(neg_list))):#限制條件 當(dāng)數(shù)的位數(shù)小于最小值位數(shù)時(shí)
            neg_values_lists=[[] for n in range(10)]#初始化數(shù)值列表 每位出現(xiàn)的值只可能是0~9 所以創(chuàng)建10個(gè)數(shù)值列表
            for neg_num in neg_list:#對(duì)于數(shù)列中的每個(gè)數(shù)
                neg_values_lists[int(neg_num/(10**neg_num_digit))%10].append(neg_num)
                #在第neg_num_digit+1次循環(huán)就比較該數(shù)的第n位上的數(shù)值 把該數(shù)添加到對(duì)應(yīng)的數(shù)值列表 比如第一次循環(huán)就比較個(gè)位 第二次比較十位
            neg_list.clear()#清空原數(shù)列用來填充有序的數(shù)列
            for neg_value_list in neg_values_lists:#對(duì)于數(shù)值列表中的每個(gè)列表
                for neg_num in neg_value_list:#對(duì)于每個(gè)列表中的每個(gè)數(shù)
                    neg_list.append(neg_num)
            neg_num_digit+=1#比較下一位

    if len(pos_list)!=0:#如果有非負(fù)數(shù)
        pos_num_digit=0#初始位數(shù)
        while pos_num_digit<len(str(max(pos_list))):#限制條件 當(dāng)數(shù)的位數(shù)小于最大值位數(shù)時(shí)
            pos_values_lists=[[] for n in range(10)]#初始化數(shù)值列表 每位出現(xiàn)的值只可能是0~9 所以創(chuàng)建10個(gè)數(shù)值列表
            for pos_num in pos_list:#對(duì)于數(shù)列中的每個(gè)數(shù)
                pos_values_lists[int(pos_num/(10**pos_num_digit))%10].append(pos_num)
                #在第pos_num_digit+1次循環(huán)就比較該數(shù)的第n位上的數(shù)值 把該數(shù)添加到對(duì)應(yīng)的數(shù)值列表比如第一次循環(huán)就比較個(gè)位 第二次比較十位
            pos_list.clear()#清空原數(shù)列用來填充有序的數(shù)列
            for pos_value_list in pos_values_lists:#對(duì)于數(shù)值列表中的每個(gè)列表
                for pos_num in pos_value_list:#對(duì)于每個(gè)列表中的每個(gè)數(shù)
                    pos_list.append(pos_num)
            pos_num_digit+=1#比較下一位
    result_list=neg_list+pos_list#結(jié)果列表
    return result_list


#記錄每一種排序算法對(duì)于不同長度無序數(shù)列的排序時(shí)間
sorts_time_dict={
            bubble_sort:['Bubble Sort'],#冒泡排序
            select_sort:['Select Sort'],#選擇排序
            insert_sort:['Insert Sort'],#插入排序
            shell_sort:['Shell Sort'],#希爾排序
            merge_sort:['Merge Sort'],#歸并排序
            quick_sort:['Quick Sort'],#快速排序
            heap_sort:['Heap Sort'],#堆排序
            count_sort:['Count Sort'],#計(jì)數(shù)排序
            bucket_sort:['Bucket Sort'],#桶排序
            radix_sort:['Radix Sort'],#基數(shù)排序
}


for num_list in nums_lists:#由于兩層for循環(huán)會(huì)使對(duì)數(shù)列進(jìn)行快速排序時(shí)的遞歸太深 會(huì)引起python崩潰 單獨(dú)對(duì)每個(gè)數(shù)列進(jìn)行快速排序
    print('正在對(duì)第'+str(nums_lists.index(num_list)+1)+'個(gè)'+'長為'+str(len(num_list))+'的隨機(jī)數(shù)列執(zhí)行Quick Sort算法')
    start_time=process_time()#開始計(jì)時(shí) 計(jì)時(shí)部分為排序算法
    quick_sort(num_list)
    end_time=process_time()#結(jié)束計(jì)時(shí)
    sorts_time_dict[quick_sort].append(end_time-start_time)#記錄每種排序算法對(duì)不同長度數(shù)列的排序時(shí)間 單位為秒
for num_list in nums_lists:#對(duì)每個(gè)數(shù)列進(jìn)行每一種排序算法
    for func_sort,time_list in sorts_time_dict.items():
        if func_sort!=quick_sort:
            print('正在對(duì)第'+str(nums_lists.index(num_list)+1)+'個(gè)'+'長為'+str(len(num_list))+'的隨機(jī)數(shù)列執(zhí)行'+time_list[0]+'算法')
            start_time=process_time()#開始計(jì)時(shí) 計(jì)時(shí)部分為排序算法
            func_sort(num_list.copy())#排序算法 .copy() 復(fù)制品 防止改變?cè)瓟?shù)列
            end_time=process_time()#結(jié)束計(jì)時(shí)
            time_list.append(end_time-start_time)#記錄每種排序算法對(duì)不同長度數(shù)列的排序時(shí)間 單位為秒
print()
print('十種排序算法對(duì)于不同長度的隨機(jī)無序數(shù)列的排序時(shí)間結(jié)果如下:')
print('{:20s}{:<15d}{:<15d}{:<15d}{:<15d}'.format('Length of Series:',500,1000,5001,10000))#格式化輸出
for time_list in sorts_time_dict.values():#每種算法
    for sort_time in time_list:#每種算法的名稱和其處理每個(gè)數(shù)列的時(shí)間
        if not isinstance(sort_time,float):#如果use_time類型不為float 即為名稱
            print('{:20s}'.format(sort_time+':'),end='')
        else:
            print('{:<15.4f}'.format(sort_time),end='')#左對(duì)齊 保留四位小數(shù)
    print()
print('單次隨機(jī)數(shù)列排序時(shí)間結(jié)果不代表所有')
print()

count_sort_list=[]#因?yàn)橛?jì)數(shù)排序太快了,單獨(dú)創(chuàng)建一個(gè)長度為100000的數(shù)列來測(cè)試排序時(shí)間
for n in range(100000):
    count_sort_list.append(randint(-80000,100000))
start_time_count_sort=process_time()#開始計(jì)時(shí) 計(jì)時(shí)部分為排序算法
count_sort(count_sort_list.copy())
end_time_count_sort=process_time()#結(jié)束計(jì)時(shí)
print('計(jì)數(shù)排序一個(gè)長度為100000的隨機(jī)數(shù)列所用時(shí)間為'+str(round(end_time_count_sort-start_time_count_sort,3))+'秒')

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容