在Python中处理list.index(可能不存在)的最佳方法是什么?

172 投票
16 回答
180720 浏览
提问于 2025-04-15 18:26

我有一段代码,看起来像这样:

thing_index = thing_list.index(thing)
otherfunction(thing_list, thing_index)

这只是个简化的例子,但你大概明白我的意思了。现在,thing 可能不在列表里,如果是这样的话,我想把 -1 作为 thing_index 传递。在其他编程语言中,如果找不到这个元素,index() 通常会返回这个值。实际上,它会抛出一个 ValueError 错误。

我可以这样做:

try:
    thing_index = thing_list.index(thing)
except ValueError:
    thing_index = -1
otherfunction(thing_list, thing_index)

但这样做让我感觉不太好,而且我也不知道 ValueError 是否会因为其他原因被抛出。我想出了一个基于生成器函数的解决方案,但看起来有点复杂:

thing_index = ( [(i for i in xrange(len(thing_list)) if thing_list[i]==thing)] or [-1] )[0]

有没有更简单的方法来实现同样的功能呢?假设这个列表是没有排序的。

16 个回答

22

dict类型在Python中有一个叫做get的功能。这个功能的意思是,如果你想查找的键在字典里不存在,那么get的第二个参数就是它返回的默认值。类似的,还有一个叫setdefault的功能,它会先检查这个键是否存在。如果存在,就返回这个键对应的值;如果不存在,就根据你提供的默认值设置这个键的值,然后返回这个默认值。

你还可以扩展list类型,给它添加一个叫getindexdefault的方法。

class SuperDuperList(list):
    def getindexdefault(self, elem, default):
        try:
            thing_index = self.index(elem)
            return thing_index
        except ValueError:
            return default

这个方法可以像这样使用:

mylist = SuperDuperList([0,1,2])
index = mylist.getindexdefault( 'asdf', -1 )
83

使用try-except语句并没有什么“脏”的地方。这是Python编程的标准做法。只有在你调用.index方法时,才会出现ValueError错误,因为那是你代码中唯一可能出错的地方!

关于评论的回答:
在Python中,有一种哲学叫做先请求宽恕,而不是请求许可,这个理念已经深入人心。而且没有任何其他问题会导致index出现这种类型的错误。我想不出还有什么其他情况会这样。

84
thing_index = thing_list.index(elem) if elem in thing_list else -1

一行代码。简单明了。没有例外。

撰写回答