选择排序及其Python实现【算法图解】

1. 引出问题

假设你的手机中存储了很多乐曲,对于每个乐队,你都记录了其作品被播放的次数。

乐队播放次数
RADIOHEAD156
KISHOKE KUMAR141
THE BLACK KEYS35
NEUTRAL MILK HOTEL94
BECK88
THE STROKES61
WILCO11

你想将乐队按照播放次数从多到少进行排列,从而将你喜欢的乐队排序,怎么做呢?

2. 选择排序

最简单的办法就是,我们从列表中选择出播放次数最多的乐队,将其转移到一个新列表中:

乐队播放次数👉乐队播放次数
RADIOHEAD156RADIOHEAD156
KISHOKE KUMAR141
THE BLACK KEYS35
NEUTRAL MILK HOTEL94
BECK88
THE STROKES61
WILCO11

这里为了确定最大播放量,我们需要检查所有的元素n=7。

再次进行同样的操作,找出播放量第二的乐队,将其转移到新列表中:

乐队播放次数👉乐队播放次数
RADIOHEAD156
KISHOKE KUMAR141KISHOKE KUMAR141
THE BLACK KEYS35
NEUTRAL MILK HOTEL94
BECK88
THE STROKES61
WILCO11

这次我们检查了n-1=6个元素。

继续这样,我们共执行n=7次这样的操作,可以得到一个有序的列表:

乐队播放次数👉乐队播放次数
RADIOHEAD156
KISHOKE KUMAR141
NEUTRAL MILK HOTEL94
BECK88
THE STROKES61
THE BLACK KEYS35
WILCO11

这里,我们即完整的展现了一次选择排序的算法流程

我们共执行了多少次元素检查呢?这是一个等差数列:n,n-1,n-2,…,2,1;

求和很简单,套公式:sum=n×(n+1)/2=n²/2+n/2,在用大O表示法表示时,因1/2是常数,直接省略,n相对于n²是小量,省略。

因此,选择的排序的运行速度为:O(n²)

3. Python代码(降序排列)

键入以下代码并运行:

## findSmallest函数作用:找到一个列表中的最小值
## 输入:
##      arr:传入的列表
## 输出:
##      smallestIndex:最小值在列表中的索引位置
def findSmallest(arr):
    smallest=arr[0] # 初始化最小值为列表的第一个值
    smallestIndex=0 # 列表的第一个值索引为0

    for i in range(1,len(arr)): # 遍历列表索引,从1到末尾
        if smallest>arr[i]:  # 如果当前最小值比列表中的值大,那么更新最小值和索引
            smallest=arr[i]
            smallestIndex=i;
    return smallestIndex # 完成遍历后,返回最小值索引

## selectSort函数作用:执行选择排序,升序排列
## 输入:
##      arr:传入的列表
## 输出:
##      newArr:排序完成的列表
def selectionSort(arr):
    newArr=[] # 初始化输出列表
    for i in range(len(arr)): # 遍历列表,找到最小值,放入新列表
        smallest=findSmallest(arr)
        newArr.append(arr.pop(smallest)) # 在原来的列表中弹出最小值,转移到新列表中
    return newArr # 完成遍历后,输出列表

## 测试代码
print(selectionSort([156,141,94,88,61,35,11]))

这里代码中的注释比较清楚,因此不再赘述,结果如下:
在这里插入图片描述

4. 更快的实现(快速排序)

选择排序比较灵巧,但是执行速度较慢。

快速排序是一种更快的算法,其运行时间为O(n×log n),有兴趣可以看看:快速排序

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值