Python:在列表中查找元素

228

在Python中,查找列表中元素的索引有哪些好的方法?请注意,该列表可能未排序。

是否有一种方法可以指定要使用的比较运算符?


2
可以将此问题取消标记为重复,因为问题和答案没有处理符合条件的类实例的情况。 - Caveman
在列表中查找项目的索引并不等同于在列表中查找项目。 - mikemaccana
10个回答

316

来自Dive Into Python

>>> li
['a', 'b', 'new', 'mpilgrim', 'z', 'example', 'new', 'two', 'elements']
>>> li.index("example")
5

19
当元素不在列表中时,这段代码会出现错误。在当前的示例情境中,如果我搜索“three”(即li.index('three')),会出现错误。 - Kedar.Aitawdekar
12
你可以通过捕获错误来检测某个东西是否在列表中。try: li.index("three") except ValueError: found = false - Peter G
2
如果您真的想要找到索引,则首先检查数组中的元素,如果为true,则执行=> li.index("example") - yogesh mhetre

176

如果您只想查找一个元素是否包含在列表中:

>>> li
['a', 'b', 'new', 'mpilgrim', 'z', 'example', 'new', 'two', 'elements']
>>> 'example' in li
True
>>> 'damn' in li
False

72

最好的方法可能是使用 列表方法.index。对于列表中的对象,您可以进行如下操作:

def __eq__(self, other):
    return self.Value == other.Value

与任何您需要的特殊处理一起使用。

您还可以使用带有enumerate(arr)的for/in语句。

查找具有值> 100的项的索引的示例。

for index, item in enumerate(arr):
    if item > 100:
        return index, item

来源


61

以下是另一种使用列表推导的方式(有些人可能会觉得它有争议性)。对于简单的测试非常容易上手,例如比较对象属性(我经常需要这样做):

el = [x for x in mylist if x.attr == "foo"][0]

当然,这假定列表中存在一个合适的元素(实际上是唯一的)。


10
el = [x for x in mylist if x.attr == "foo"] 的意思是筛选出 mylist 中所有 attr 属性为 "foo" 的元素,并将其存储在列表 el 中。if el: do something with el[0] 的意思是,如果列表 el 不为空,则对其中的第一个元素执行某些操作。这种写法解决了“存在性”问题。 - berkus
15
el = next((x for x in mylist if x.attr == "foo"), None),如果你希望即使没有符合条件的值也能得到返回结果。 - Thiago Lages de Alencar
2
[*[label_set for label_set in prediction_label_sets if x == 3], None][0] 如果你想要回退到 none,而不使用迭代器。不确定它是更简单还是更复杂。 - Sebastian

19

假设你想在NumPy数组中查找一个值,我猜这样做可能有效:

Numpy.where(arr=="value")[0]

1
如果你想查找特定行,例如 arr = np.array([[0,0,1],[0,1,0],[1,0,0]]),则该方法不适用于多维数组。如果你执行 np.where(arr == [0,1,0]),它将无法给出正确的结果。 - ierdna
@ierdna,你需要提供axis=0axis=1吗? - mLstudent33

8

有一个 index 方法, i = array.index(value), 但我不认为你可以指定一个自定义比较操作符。不过,编写自己的函数来实现这一点并不难:

def custom_index(array, compare_function):
    for i, v in enumerate(array):
        if compare_function(v):
            return i

6

我使用这个函数来返回匹配元素的索引(Python 2.6):

def index(l, f):
     return next((i for i in xrange(len(l)) if f(l[i])), None)

然后通过lambda函数使用它来检索所需的元素,例如通过使用元素名称的方程式。

element = mylist[index(mylist, lambda item: item["name"] == "my name")]

如果我需要在代码中的多个地方使用它,我可以定义特定的查找函数,例如通过名称查找元素:

def find_name(l, name):
     return l[index(l, lambda item: item["name"] == name)]

然后这非常容易和易于阅读:
element = find_name(mylist,"my name")

4
列表的索引方法可以为你完成此操作。如果你想保证顺序,请先使用 sorted() 对列表进行排序。Sorted 接受 cmp 或 key 参数来指定排序方式:
a = [5, 4, 3]
print sorted(a).index(5)

或者:

a = ['one', 'aardvark', 'a']
print sorted(a, key=len).index('a')

3

我通过调整一些教程找到了这个。感谢Google和你们所有人的帮助;)

def findall(L, test):
    i=0
    indices = []
    while(True):
        try:
            # next value in list passing the test
            nextvalue = filter(test, L[i:])[0]

            # add index of this value in the index list,
            # by searching the value in L[i:] 
            indices.append(L.index(nextvalue, i))

            # iterate i, that is the next index from where to search
            i=indices[-1]+1
        #when there is no further "good value", filter returns [],
        # hence there is an out of range exeption
        except IndexError:
            return indices

一个非常简单的用法:
a = [0,0,2,1]
ind = findall(a, lambda x:x>0))

[2, 3]

附言:请原谅我的英语


2
这个怎么样?
def global_index(lst, test):
    return ( pair[0] for pair in zip(range(len(lst)), lst) if test(pair[1]) )

使用方法:

>>> global_index([1, 2, 3, 4, 5, 6], lambda x: x>3)
<generator object <genexpr> at ...>
>>> list(_)
[3, 4, 5]

3
让我们写出更符合 Python 风格的代码: 定义一个函数 global_index(lst, test),该函数接受两个参数:一个列表 lst 和一个测试函数 test,并返回满足测试函数的列表元素的索引。 具体实现方式是使用 Python 内置函数 enumerate() 来遍历 lst 列表,同时通过 test(val) 的判断条件来筛选出满足要求的元素,最终将它们的索引用生成器表达式 (idx for idx, val in enumerate(lst) if test(val)) 输出。 - recursive
6
filter(lambda x: x>3, [1,2,3,4,5,6])这行代码的意思是:使用lambda函数过滤列表[1,2,3,4,5,6]中大于3的元素。 - John Fouhy

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接