排序算法

#-*-coding:utf-8-*-
#冒泡排序
#工作原理:冒泡排序通过依次交换相邻两个顺序不合法的元素位置,从而将当前最小(大)元素放到合适的位置;
#时间复杂度:为O(n2)----貌似按照最差情况计算时间复杂度,也就是逆序的情况下进行正序排序
def bubble(list):
    for i in range(0,len(list)-1): #需要比较的次数,因为最后一各数字不用再比较,所以次数是长度减1
        flag = False
        for j in range(0,len(list)-1-i): #每一轮比较结束后,待比较的长度减1
            if list[j] > list[j+1]:
                list[j],list[j+1] = list[j+1],list[j]
                flag = True
        if flag == False:  #当上一次排序没有交换,说明已经排好序了,不用再循环比较了;
                return list
    return list

#简单选择排序
#工作原理: 一趟遍历选择最小的数放在第一位,再进行下一次遍历直到最后一个元素
# 简单选择排序法(Simple Selection Sort)就是通过n-i次关键字间的比较,从n-i+1个记录中选出关键字最小的记录,并和第i(1≤i≤n)个记录交换之。
#时间复杂度:为O(n2),但简单选择排序的性能上还是要略优于冒泡排序
def selectionSort(list):
    for i in range(len(list)-1):  #因为最后一个值就没有再后面比较的元素了,所以减1
        min = i  #假设起始位置为最小值
        for j in range(i+1,len(list)): #最小值与第i+1及以后的元素做比较,
            if list[min] > list[j]: #如果有比list[min]小的值,就交换两者的下标,每一轮j循环后,找到一个最小值
                min = j
        if min <> i: #若min不等于i,说明找到最小值,交换;如果相等,说明排序完毕,不用再交换了,再交换就乱套了,所以要判断min和i是否相等;
            list[min],list[j] = list[j],list[min]  #交换设定最小值与实际最小值的位置,每一次i循环交换一次,
                                                   # i值往后移动(也就是min的位置往后移动),开始寻找次小及其他更小的值;
    print list



#直接插入排序
#工作原理:将列表分为有序区和无序区,最开始的有序区只有一个元素,每次从无序区选择一个元素按大小插到有序区中
#          从无序区中取到的值分别于有序区比较,并且从有序区的最后面的值开始比,如果小,插入到前面
#时间复杂度:为O(n2),但比冒泡和简单选择排序的性能要好一些
def insertSort(list):
    for i in range(1,len(list)):  #因为range(0,1)返回的值[0],所以这里是range(1,len(list));而且最后一个值也是无序区中的值,需要跟前面的做比较
        temp = list[i]      #list[0]为初始有序区,从无序区顺次取值比较,list[1]为无序区第一个值
        for j in range(i-1,-1,-1):  #从有序区最大值开始遍历,也就是有序区从后面的值依次往前比较;最后的值最大(因为是有序区啊)
            if list[j]>temp:    #如果待插入的无序区的值小于有序区的值
                list[j+1] = list[j] #有序区的值向后挪一位
                list[j] = temp  #将无序区的值temp放进去,插入到正确的位置
    print list

#快速排序
#工作原理:通过一趟排序将待排记录分割成独立的两部分,其中一部分记录的关键字均比另一部分记录的关键字小,
# 则可分别对这两部分记录继续进行排序,以达到整个序列有序的目的
#时间复杂度:

def partition(list,low,high):  #计算枢轴值pivot的位置,使它之前(后)位置的元素不大于(小于)它
    mid = (low+high)/2
    if list[low] > list[high]:
        list[high],list[low] = list[low],list[high]
    if list[mid] > list[high]:
        list[high],list[mid] = list[mid],list[high]
    if list[low] < list[mid]:
        list[low],list[mid] = list[mid],list[low]
    pivotkey = list[low]  #选低位、高位、中间位上的三个数,选择不大不小的那个数并放到低位,作为中轴数
    while low < high:  #从表的两端交替地向中间扫描
        while (low < high) and (list[high] >= pivotkey):
            high -=1
        list[low],list[high] = list[high],list[low]  #将比枢轴记录小的记录交换到低端
        while (low < high) and (list[low] <= pivotkey):
            low +=1
        list[high],list[low] = list[low],list[high]  #将比枢轴记录大的记录交换到高端
    return low  #返回枢轴所在位置

#/对顺序表list中的子序列作快速排序
def qsort(list,low,high):
    if low < high:
        pivot = partition(list,low,high)  #将list列表一分为二,算出枢轴值pivot
        qsort(list,low,pivot-1)  #对低子表递归排序
        qsort(list,pivot+1,high)  #对高子表递归排序

def quickSort(list):
    qsort(list,0,len(list)-1)
    return list

#快速排序2
def QuickSort(myList,start,end):
    #判断low是否小于high,如果为false,直接返回
    if start < end:
        i,j = start,end
        #设置基准数
        base = myList[i]
        # 从表的两端交替向中间扫描
        while i < j:
            #如果列表后边的数,比基准数大或相等,则前移一位直到有比基准数小的数出现
            while (i < j) and (myList[j] >= base):
                j = j - 1
            #如找到,则把第j个元素赋值给第i个元素,此时表中i,j个元素相等
            myList[i] = myList[j]
            #同样的方式比较前半区
            while (i < j) and (myList[i] <= base):
                i = i + 1
            myList[j] = myList[i]
        #做完第一轮比较之后,列表被分成了两个半区,并且i=j,需要将这个数设置回base
        myList[i] = base
        #递归前后半区
        QuickSort(myList, start, i - 1)
        QuickSort(myList, j + 1, end)
    return myList


if __name__ == "__main__":
    list = [50,10,90,30,70,40,80,60,20]
    # print bubble(list)
    # selectionSort(list)
    # insertSort(list)
    print QuickSort(list,0,len(list)-1)
    #print quickSort(list)

 

posted on 2018-09-07 17:02  欢喜等大年  阅读(115)  评论(0编辑  收藏  举报

导航