python数据结构第五天

排序和简单地搜索

排序算法的稳定性
稳定性:稳定排序算法会让原本有相等键值的纪录维持相对次序。
假设以下的数对将要以他们的第一个数字来排序。

(4, 1)  (3, 1)  (3, 7)(5, 6)

在这个状况下,有可能产生两种不同的结果,一个是让相等键值的纪录维持相对的次序,而另外一个则没有:

(3, 1)  (3, 7)  (4, 1)  (5, 6)  (维持次序)
(3, 7)  (3, 1)  (4, 1)  (5, 6)  (次序被改变)

那么低一个就是稳定的,第二个就是不稳定的

冒泡排序

def bubble_sort(alist):
    for j in range(len(alist)-1,0,-1):
     # j表示每次遍历需要比较的次数
        for i in range(j):
              if alist[i]>alist[i+1]:
                  alist[i],alist[i+1]=alist[i+1],alist[i]

li = [54,26,93,17,77,31,44,55,20]
bubble_sort(li)
print(li)

输出

[17, 20, 26, 31, 44, 54, 55, 77, 93]

选择排序

def selection_sort(alist):
    n=len(alist)
    for i in range(n-1):
    #i代表将要选择第i个位置的元素
        min_index=i
        for j in range(i+1,n):
            #j代表本次选择从第j个开始
            if alist[min_index]>alist[j]:
                min_index=j
        if min_index!=i:
            alist[min_index],alist[i]=alist[i],alist[min_index]

alist = [54,226,93,17,77,31,44,55,20]
selection_sort(alist)
print(alist)

输出结果:

[17, 20, 31, 44, 54, 55, 77, 93, 226]

插入排序

def insert_sort(alist):
    for i in range(1,len(alist)):
        #i是指每次插入需要比较的次数
        for j in range(i-1,0,-1):
            #j是指从第j个向前比较,一直比较到第0个
            if alist[j]<alist[j-1]:
                alist[j],alist[j-1]=alist[j-1],alist[j]

alist = [54,26,93,17,77,31,44,55,20]
insert_sort(alist)
print(alist)

输出

[17, 26, 31, 44, 54, 55, 77, 93, 20]

希尔排序

希尔排序是一种高级的快速排序,每次排序的元素是列表中以某个数为间隔的子列表

def shell_sort(arr):
    n=len(arr)
    gap=n//2
    ##从一个比较大的gap开始,然后缩小gap

    while gap>0:
    #以gap为间隙进行插入排序,arr[0...gap-1]已经在即将被插入的序列中
    #每次添加一个元素进行以此gap的插入排序,直到最后一个元素

        for i in range(gap,n):
            temp=arr[i]
            #临时保存arr[i],将arr[i]添加到合适的位置

            j=i
            while j-gap>=0 and arr[j-gap]>temp:
                arr[j]=arr[j-gap]
                j-=gap
            #一直将比temp大的元素移动到arr[j+gap]上
            arr[j]=temp
        gap=gap//2

alist = [6,10,1,3,5,11,2,14]
shell_sort(alist)
print(alist)
[1, 2, 3, 5, 6, 10, 11, 14]

快速排序

def quick_sort(arr,start,end):
    if start>=end:
        return
    #退出循环的条件

    mid=arr[start]
    low=start
    high=end

    while low<high:
        # 如果low与high未重合,high指向的元素不比基准元素小,则high向左移动
        while low<high and arr[high]>mid:
            high-=1
        # 将high指向的元素放到low的位置上
        arr[low]=arr[high]
        # 如果low与high未重合,low指向的元素比基准元素小,则low向右移动
        while low<high and arr[low]<mid:
            low+=1
        # 将low指向的元素放到high的位置上
        arr[high]=arr[low]

    # 退出循环后,low与high重合,此时所指位置为基准元素的正确位置
    # 将基准元素放到该位置
    arr[low]=mid

    quick_sort(arr,start,low-1)
    quick_sort(arr,low+1,end)

alist = [54,26,93,17,77,31,44,55,20]
quick_sort(alist,0,len(alist)-1)
print(alist)
[17, 20, 26, 31, 44, 54, 55, 77, 93]

归并排序

def merge(a,b):
    c=[]
    i=j=0
    while i<len(a) and j<len(b):
        if a[i]<b[j]:
            c.append(a[i])
            i+=1
        else:
            c.append(b[j])
            j+=1
    if i<len(a):
        for k in a[i:]:
            c.append(k)
    if j<len(b):
        for l in b[j:]:
            c.append(l)
    return c

def merge_sort(arr):
    if len(arr)<=1:
        return arr 
    mid=len(arr)//2
    l=merge_sort(arr[:mid])
    r=merge_sort(arr[mid:])
    return merge(l,r)


a = [4, 7, 8, 3, 5, 9]
print(merge_sort(a))
[3, 4, 5, 7, 8, 9]

常见排序算法比较

在这里插入图片描述

二分查找法的递归与非递归

递归方式

def binary_search(arr,item):
    if len(arr)==0:
        return
    else:
        mid=len(arr)//2
        if arr[mid]==item:
            return True
        else:
            if item<arr[mid]:
                binary_search(arr[:mid],item)
            else:
                binary_search(arr[mid+1:],item)

testlist = [0, 1, 2, 8, 13, 17, 19, 32, 42,]
print(binary_search(testlist, 3))
print(binary_search(testlist, 13))
None
True

非递归方式:

def binary_search(arr,item):
    l=0
    r=len(arr)-1
    while l<=r:
        mid=(l+r)//2
        if arr[mid]==item:
            return True
        elif item<arr[mid]:
            r=mid-1
        else:
            l=mid+1
    return False


testlist = [0, 1, 2, 8, 13, 17, 19, 32, 42,]
print(binary_search(testlist, 3))
print(binary_search(testlist, 13))
False
True
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值