如果是直接得到最小或最大k个数,那么直接排序即可。但是如果要得到索引,那么不能排序,或者你排序时附带数据的下标。本文通过两种方法来展示怎么得到最小k个数的索引,一种是直接使用min()函数得到列表的最小值,然后使用index()函数得到该值的索引,循环k次即可,很方便且易于理解;另一种则是在排序中附带数据下标,最终排序结束,也可得到最小k个数在原列表的索引。
1. List.index(min(List))
List = [3, -4, 0, 6.4, -1.6, 9.09]
Lst = List[:] #对列表进行浅复制,避免后面更改原列表数据
k = 3 #此处示范得到列表最小3个数的索引
index_k = []
for i in range(k):
index_i = Lst.index(min(Lst)) #得到列表的最小值,并得到该最小值的索引
index_k.append(index_i) #记录最小值索引
Lst[index_i] = float('inf') #将遍历过的列表最小值改为无穷大,下次不再选择
print(index_k) #打印输出最小3个数的索引以及原列表的数据
for i in range(k):
print(List[index_k[i]])
在命令行终端执行结果如下图所示
2. 附带索引的快速排序
关于快排、归并排序以及选择排序算法可看我的另外一篇博客 https://blog.csdn.net/yldmkx/article/details/108367734,强烈推荐先理解快排之后,再去理解添加索引的快排算法。
def quicksort(Lp):
if len(Lp)<2:
return Lp
L = Lp[:]
key = len(L)//2
left = -1
right = len(L)
while left<right:
right -= 1 #下一轮开始都需要在上轮的值移动一步,不然又重复计算
while right>key and L[right][0]>=L[key][0]:
right -= 1
if right>key: #满足条件说明while循环是因为L[right]<L[key]而跳出,此时需要更新key
L[right], L[key] = L[key], L[right]
key = right
left += 1 #下一轮开始都需要在上轮的值移动一步,不然又重复计算
while left<key and L[left][0]<=L[key][0]:
left += 1
if key>left: #满足条件说明while循环是因为L[left]>L[key]而跳出,此时需要更新key
L[left], L[key] = L[key], L[left]
key = left
return quicksort1(L[:key]) + [L[key]] + quicksort1(L[key+1:])
Lit = [3, -4, 0, 6.4, -1.6, 9.09]
List = [[Lit[i], i] for i in range(len(Lit))] #将原列表拓展成附带索引的二维列表
L = quicksort(List) #调用快排算法
k = 3 #示范寻找最小3个数的索引
for i in rang(k): #打印列表的k个最小值以及索引
print(L[i])
执行结果如下图所示,每一次第一个数是列表的前k个最小值,第二个数是该最小值在原列表的索引,和第一种方法结果一样