在列表中找到项目的索引
内容来自 DOC https://q.houxu6.top/?s=在列表中找到项目的索引
给定一个列表 ["foo", "bar", "baz"] 和一个列表中的项目 "bar",我如何获取它的索引 1?
>>> ["foo", "bar", "baz"].index("bar")
1
查看列表的内置 .index() 方法的文档:
list.index(x[, start[, end]])返回列表中第一个值等于 x 的项目零基索引。如果没有这样的项目,则引发
ValueError。可选参数 start 和 end 解释为切片符号,并用于将搜索限制到列表的特定子序列。返回的索引是相对于完整序列的开头计算的,而不是 start 参数。
注意事项
线性时间复杂度在列表长度上
一个 index 调用按顺序检查列表中的每个元素,直到找到匹配项。如果列表很长,并且没有保证值将靠近开头,这可能会使代码变慢。
这个问题只能通过使用不同的数据结构完全避免。然而,如果元素已知位于列表的某个部分,则可以使用 start 和 end 参数来缩小搜索范围。
例如:
>>> import timeit
>>> timeit.timeit('l.index(999\_999)', setup='l = list(range(0, 1\_000\_000))', number=1000)
9.356267921015387
>>> timeit.timeit('l.index(999\_999, 999\_990, 1\_000\_000)', setup='l = list(range(0, 1\_000\_000))', number=1000)
0.0004404920036904514
第二个调用速度要快几个数量级,因为它只需要搜索10个元素,而不是100万个。
只返回第一个匹配项的索引
对 index 的调用按顺序搜索列表,直到找到匹配项,然后停止。如果有多个匹配项,并且需要所有索引,则 index 无法解决问题:
>>> [1, 1].index(1) # the `1` index is not found.
0
相反,使用 列表推导式或生成器表达式进行搜索,使用 enumerate 获取索引:
>>> # 列表推导式直接给出索引列表:
>>> [i for i, e in enumerate([1, 2, 1]) if e == 1]
[0, 2]
>>> # 生成器推导式给我们一个可迭代对象...
>>> g = (i for i, e in enumerate([1, 2, 1]) if e == 1)
>>> # 可以使用 in 循环,或者使用 next 手动迭代:
>>> next(g)
0
>>> next(g)
2
列表推导式和生成器表达式技术仍然适用于只有一个匹配项的情况,并且更具通用性。
如果找不到匹配项则引发异常
如上文文档所述,使用 .index 将在未找到搜索的值时引发异常:
>>> [1, 1].index(2)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: 2 is not in list
如果这是值得关注的问题,可以使用 item in my_list 进行显式检查,或者使用 try/except 处理异常。
显式检查简单易懂,但必须再次遍历列表。有关此选择的更多指导,请参阅 What is the EAFP principle in Python?。

浙公网安备 33010602011771号