Trouver l'indice d'un élément dans une liste contenant en Python

pour une liste ["foo", "bar", "baz"] et un élément de la liste "bar" , Comment puis-je obtenir son index (1) en Python?

2354
demandé sur Aaron Hall 2008-10-07 05:39:38
la source

27 ответов

>>> ["foo", "bar", "baz"].index("bar")
1

référence: Structures de données > pour en savoir plus sur les listes

mises en garde de suivre

notez que bien que ce soit peut-être la façon la plus propre de répondre à la question comme demandé , index est un composant plutôt faible de l'API list , et je ne me souviens pas de la dernière fois que je l'ai utilisé dans la colère. Il m'a été signalé dans les commentaires que parce que cette réponse est fortement référencée, il devrait être plus complète. Quelques mises en garde au sujet de list.index suivent. Il est probablement intéressant de jeter un coup d'oeil d'abord à la corde de Doc:

>>> print(list.index.__doc__)
L.index(value, [start, [stop]]) -> integer -- return first index of value.
Raises ValueError if the value is not present.

temps Linéaire-la complexité dans la liste de longueur

Un index appel vérifie chaque élément de la liste dans l'ordre, jusqu'à ce qu'il trouve une correspondance. Si votre liste est longue, et que vous ne savez pas à peu près où elle se trouve, cette recherche pourrait devenir un goulot d'étranglement. Dans ce cas, vous devriez envisager un structure de données différente. Notez que si vous savez à peu près où trouver la correspondance, vous pouvez donner index un indice. Par exemple, dans cet extrait, l.index(999_999, 999_990, 1_000_000) est environ cinq ordres de grandeur plus rapide que l.index(999_999) , parce que le premier n'a à rechercher que 10 entrées, tandis que le second recherche un million:

>>> 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

renvoie seulement l'index du first match à son argument

un appel à index cherche dans la liste jusqu'à ce qu'elle trouve une correspondance, et s'y arrête. si vous prévoyez avoir besoin d'indices de plus de correspondances, vous devez utiliser une liste de compréhension, ou une expression génératrice.

>>> [1, 1].index(1)
0
>>> [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)
>>> next(g)
0
>>> next(g)
2

la plupart des endroits où j'aurais utilisé index , j'utilise maintenant une expression de compréhension de liste ou de générateur parce qu'ils sont plus généralisables. Donc, si vous envisagez d'atteindre index , jetez un oeil à ces excellentes caractéristiques python.

lancer si élément non présent dans la liste

un appel à index se traduit par un ValueError si l'article n'est pas présent.

>>> [1, 1].index(2)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: 2 is not in list

si l'article pourrait ne pas être présent dans la liste, vous devez soit

  1. Vérifiez d'abord avec item in my_list (approche propre et lisible), ou
  2. Envelopper index appel à un try/except bloc qui capture ValueError (probablement plus rapide, au moins quand la liste à rechercher est longue, et l'élément est habituellement présent.)
3445
répondu Alex Coventry 2018-06-27 07:00:35
la source

une chose qui est vraiment utile dans L'apprentissage de Python est d'utiliser la fonction d'aide interactive:

>>> help(["foo", "bar", "baz"])
Help on list object:

class list(object)
 ...

 |
 |  index(...)
 |      L.index(value, [start, [stop]]) -> integer -- return first index of value
 |

qui vous mènera souvent à la méthode que vous recherchez.

795
répondu davidavr 2008-10-07 17:19:56
la source

la majorité des réponses expliquent comment trouver un index unique , mais leurs méthodes ne renvoient pas les index multiples si l'article est dans la liste plusieurs fois. Utilisation enumerate() :

for i, j in enumerate(['foo', 'bar', 'baz']):
    if j == 'bar':
        print(i)

la fonction index() renvoie uniquement la première occurrence, tandis que enumerate() renvoie toutes les occurrences.

comme liste de compréhension:

[i for i, j in enumerate(['foo', 'bar', 'baz']) if j == 'bar']

voici aussi une autre petite solution avec itertools.count() (qui est à peu près la même approche que énumérer):

from itertools import izip as zip, count # izip for maximum efficiency
[i for i, j in zip(count(), ['foo', 'bar', 'baz']) if j == 'bar']

Ceci est plus efficace pour les listes plus grandes que l'utilisation de enumerate() :

$ python -m timeit -s "from itertools import izip as zip, count" "[i for i, j in zip(count(), ['foo', 'bar', 'baz']*500) if j == 'bar']"
10000 loops, best of 3: 174 usec per loop
$ python -m timeit "[i for i, j in enumerate(['foo', 'bar', 'baz']*500) if j == 'bar']"
10000 loops, best of 3: 196 usec per loop
457
répondu TerryA 2017-11-02 02:55:58
la source

pour obtenir tous les index:

 indexes = [i for i,x in enumerate(xs) if x == 'foo']
130
répondu FMc 2017-12-23 19:43:48
la source

index() retourne le premier indice de valeur!

/ index(...)

/ L. index (value, [start, [stop]) - > entier -- retour premier index de valeur

def all_indices(value, qlist):
    indices = []
    idx = -1
    while True:
        try:
            idx = qlist.index(value, idx+1)
            indices.append(idx)
        except ValueError:
            break
    return indices

all_indices("foo", ["foo","bar","baz","foo"])
109
répondu HongboZhu 2012-03-09 14:38:09
la source

Un problème se pose si l'élément n'est pas dans la liste. Cette fonction traite la question:

# if element is found it returns index of element else returns None

def find_element_in_list(element, list_element):
    try:
        index_element = list_element.index(element)
        return index_element
    except ValueError:
        return None
67
répondu tanzil 2017-04-24 13:00:10
la source
a = ["foo","bar","baz",'bar','any','much']

indexes = [index for index in range(len(a)) if a[index] == 'bar']
58
répondu savinson 2017-10-31 10:45:46
la source

vous devez définir une condition pour vérifier si l'élément que vous recherchez est dans la liste

if 'your_element' in mylist:
    print mylist.index('your_element')
else:
    print None
40
répondu user3670684 2014-05-26 08:26:52
la source

toutes les fonctions proposées ici reproduisent un comportement de langage inhérent mais obscurcissent ce qui se passe.

[i for i in range(len(mylist)) if mylist[i]==myterm]  # get the indices

[each for each in mylist if each==myterm]             # get the items

mylist.index(myterm) if myterm in mylist else None    # get the first index and fail quietly

Pourquoi écrire une fonction avec manipulation d'exception si le langage fournit les méthodes pour faire ce que vous voulez lui-même?

36
répondu Graham Giller 2016-12-24 17:24:33
la source

si vous voulez tous les index, alors vous pouvez utiliser NumPy :

import numpy as np

array = [1, 2, 1, 3, 4, 5, 1]
item = 1
np_array = np.array(array)
item_index = np.where(np_array==item)
print item_index
# Out: (array([0, 2, 6], dtype=int64),)

c'est une solution claire et lisible.

29
répondu rbrisuda 2018-06-04 23:26:33
la source

trouver l'index d'un article donné une liste le contenant en Python

pour une liste ["foo", "bar", "baz"] et un article dans la liste "bar" , Quel est le moyen le plus propre pour obtenir son index (1) en Python?

bien sûr, il y a la méthode index, qui renvoie l'index de la première occurrence:

>>> l = ["foo", "bar", "baz"]
>>> l.index('bar')
1

il y a quelques problèmes avec cette méthode:

  • si la valeur n'est pas dans la liste, vous obtiendrez un ValueError
  • si plus d'une valeur est dans la liste, vous obtenez seulement l'index de la première

Non valeurs

si la valeur peut manquer, vous devez attraper le ValueError .

vous pouvez le faire avec une définition réutilisable comme celle-ci:

def index(a_list, value):
    try:
        return a_list.index(value)
    except ValueError:
        return None

et l'utiliser comme ceci:

>>> print(index(l, 'quux'))
None
>>> print(index(l, 'bar'))
1

et l'inconvénient de ceci est que vous aurez probablement un contrôle pour si la valeur retournée is ou is not aucun:

result = index(a_list, value)
if result is not None:
    do_something(result)

Plus d'une valeur dans la liste

si vous pouviez avoir plus d'occurrences, vous pas obtenez des informations complètes avec list.index :

>>> l.append('bar')
>>> l
['foo', 'bar', 'baz', 'bar']
>>> l.index('bar')              # nothing at index 3?
1

vous pourriez énumérer dans une liste la compréhension index:

>>> [index for index, v in enumerate(l) if v == 'bar']
[1, 3]
>>> [index for index, v in enumerate(l) if v == 'boink']
[]

si vous n'avez pas d'occurrences, vous pouvez vérifier cela avec la vérification booléenne du résultat, ou tout simplement ne rien faire si vous boucle sur les résultats:

indexes = [index for index, v in enumerate(l) if v == 'boink']
for index in indexes:
    do_something(index)

Meilleures données munging avec les pandas

si vous avez pandas, vous pouvez facilement obtenir cette information avec un objet de série:

>>> import pandas as pd
>>> series = pd.Series(l)
>>> series
0    foo
1    bar
2    baz
3    bar
dtype: object

un contrôle de comparaison retournera une série de booléens:

>>> series == 'bar'
0    False
1     True
2    False
3     True
dtype: bool

passer cette série de booléens à la série via la notation en indice, et vous obtenez juste les membres correspondants:

>>> series[series == 'bar']
1    bar
3    bar
dtype: object

si vous voulez juste les index, l'attribut index renvoie une série d'entiers:

>>> series[series == 'bar'].index
Int64Index([1, 3], dtype='int64')

Et si vous les voulez dans une liste ou un tuple, juste passer du constructeur:

>>> list(series[series == 'bar'].index)
[1, 3]

Oui, vous pourriez utiliser une compréhension de liste avec énumérer aussi, mais ce n'est pas aussi élégant, à mon avis - vous faites des tests pour l'égalité en Python, au lieu de laisser le code écrit en C le gérer:

>>> [i for i, value in enumerate(l) if value == 'bar']
[1, 3]

Est-ce un XY problème ?

le problème XY est de demander votre solution tentée plutôt que votre problème réel.

Pourquoi pensez-vous que vous avez besoin de l'index donné un élément dans une liste?

si vous connaissez déjà la valeur, pourquoi vous souciez-vous où il est dans une liste?

si la valeur n'est pas là, attraper le ValueError est plutôt verbeux - et je préfère éviter cela.

je suis habituellement itérating au-dessus de la liste de toute façon, donc je vais généralement garder un pointeur à toute information intéressante, obtenir le index avec enumerate.

si vous êtes munging data, vous devriez probablement utiliser pandas-qui a loin des outils plus élégants que les pythons purs que j'ai montrés.

Je ne me souviens pas avoir eu besoin de list.index , moi-même. Cependant, j'ai regardé à travers la bibliothèque standard de Python, et je vois d'excellentes utilisations pour elle.

il y a beaucoup, beaucoup d'utilisations pour elle dans idlelib , pour GUI et parsing de texte.

le module keyword l'utilise pour trouver des marqueurs de commentaires dans le module pour régénérer automatiquement la liste de mots-clés en elle via métaprogrammation.

In Lib/mailbox.py il semble l'utiliser comme une cartographie ordonnée:

key_list[key_list.index(old)] = new

et

del key_list[key_list.index(key)]

Lib/http/cookiejar.py, semble être utilisé pour obtenir le mois prochain:

mon = MONTHS_LOWER.index(mon.lower())+1

Lib/tarfile.py semblable à distutils pour obtenir une tranche jusqu'à un élément:

members = members[:members.index(tarinfo)]

In Lib/pickletools.py:

numtopop = before.index(markobject)

ce que ces usages semblent avoir en commun est qu'ils semblent fonctionner sur des listes de tailles limitées (important en raison de O(n) le temps de recherche pour list.index ), et ils sont principalement utilisés dans l'analyse (et L'UI dans le cas de ralenti).

bien qu'il existe des cas d'utilisation, ils sont assez rares. Si vous cherchez cette réponse, demandez-vous si ce que vous faites est l'utilisation la plus directe des outils fournis par la langue pour votre cas d'utilisation.

22
répondu Aaron Hall 2017-09-03 02:56:20
la source

tous les index avec la zip fonction:

get_indexes = lambda x, xs: [i for (y, i) in zip(xs, range(len(xs))) if x == y]

print get_indexes(2, [1, 2, 3, 4, 5, 6, 3, 2, 3, 2])
print get_indexes('f', 'xsfhhttytffsafweef')
19
répondu Arnaldo P. Figueira Figueira 2018-06-04 23:50:20
la source

tout simplement vous pouvez aller avec

a = [['hand', 'head'], ['phone', 'wallet'], ['lost', 'stock']]
b = ['phone', 'lost']

res = [[x[0] for x in a].index(y) for y in b]
15
répondu octoback 2013-05-29 11:17:15
la source

une autre option

>>> a = ['red', 'blue', 'green', 'red']
>>> b = 'red'
>>> offset = 0;
>>> indices = list()
>>> for i in range(a.count(b)):
...     indices.append(a.index(b,offset))
...     offset = indices[-1]+1
... 
>>> indices
[0, 3]
>>> 
15
répondu Mathitis2Software 2013-05-29 23:17:21
la source

une variante sur la réponse de FMc et user7177 donnera un dict qui peut retourner tous les indices pour n'importe quelle entrée:

>>> a = ['foo','bar','baz','bar','any', 'foo', 'much']
>>> l = dict(zip(set(a), map(lambda y: [i for i,z in enumerate(a) if z is y ], set(a))))
>>> l['foo']
[0, 5]
>>> l ['much']
[6]
>>> l
{'baz': [2], 'foo': [0, 5], 'bar': [1, 3], 'any': [4], 'much': [6]}
>>> 

Vous pouvez également utiliser une doublure pour obtenir tous les indices pour une seule entrée. Il n'y a aucune garantie d'efficacité, bien que j'ai utilisé set(a) pour réduire le nombre de fois où la lambda est appelée.

13
répondu bvanlew 2014-03-28 13:11:57
la source

et maintenant, pour quelque chose de complètement différent...

... comme confirmer l'existence de l'article avant d'obtenir l'index. La bonne chose à propos de cette approche est la fonction retourne toujours une liste d'indices-même si c'est une liste vide. Il fonctionne avec des chaînes.

def indices(l, val):
    """Always returns a list containing the indices of val in the_list"""
    retval = []
    last = 0
    while val in l[last:]:
            i = l[last:].index(val)
            retval.append(last + i)
            last += i + 1   
    return retval

l = ['bar','foo','bar','baz','bar','bar']
q = 'bar'
print indices(l,q)
print indices(l,'bat')
print indices('abcdaababb','a')

lorsqu'il est collé dans une fenêtre Python interactive:

Python 2.7.6 (v2.7.6:3a1db0d2747e, Nov 10 2013, 00:42:54) 
[GCC 4.2.1 (Apple Inc. build 5666) (dot 3)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> def indices(the_list, val):
...     """Always returns a list containing the indices of val in the_list"""
...     retval = []
...     last = 0
...     while val in the_list[last:]:
...             i = the_list[last:].index(val)
...             retval.append(last + i)
...             last += i + 1   
...     return retval
... 
>>> l = ['bar','foo','bar','baz','bar','bar']
>>> q = 'bar'
>>> print indices(l,q)
[0, 2, 4, 5]
>>> print indices(l,'bat')
[]
>>> print indices('abcdaababb','a')
[0, 4, 5, 7]
>>> 

mise à Jour

après une autre année de développement en tête-à-tête python, je suis un peu gêné par ma réponse originale, donc pour mettre les choses au clair, on peut certainement utiliser le code ci-dessus; cependant, le beaucoup façon plus idiomatique d'obtenir le même comportement serait d'utiliser la compréhension de liste, avec la fonction énumerate ().

quelque chose comme ça:

def indices(l, val):
    """Always returns a list containing the indices of val in the_list"""
    return [index for index, value in enumerate(l) if value == val]

l = ['bar','foo','bar','baz','bar','bar']
q = 'bar'
print indices(l,q)
print indices(l,'bat')
print indices('abcdaababb','a')

qui, lorsqu'il est collé dans une fenêtre Python interactive donne:

Python 2.7.14 |Anaconda, Inc.| (default, Dec  7 2017, 11:07:58) 
[GCC 4.2.1 Compatible Clang 4.0.1 (tags/RELEASE_401/final)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> def indices(l, val):
...     """Always returns a list containing the indices of val in the_list"""
...     return [index for index, value in enumerate(l) if value == val]
... 
>>> l = ['bar','foo','bar','baz','bar','bar']
>>> q = 'bar'
>>> print indices(l,q)
[0, 2, 4, 5]
>>> print indices(l,'bat')
[]
>>> print indices('abcdaababb','a')
[0, 4, 5, 7]
>>> 

et maintenant, après avoir examiné cette question et toutes les réponses, je me rends compte que c'est exactement ce que FMc suggéré dans sa réponse précédente . Au moment où j'ai répondu à cette question, je n'ai même pas voir cette réponse, parce que je ne l'ai pas compris. J'espère que mon exemple un peu plus verbeux aidera la compréhension.

si la seule ligne de code au-dessus de still n'a pas de sens pour vous, je vous recommande fortement Google 'Python list comprehension' et prendre quelques minutes pour vous familiariser. C'est juste l'une des nombreuses fonctionnalités puissantes qui en font un plaisir d'utiliser Python pour développer du code.

13
répondu MrWonderful 2018-07-18 13:01:05
la source

obtention de tous les événements et de la position d'un ou plusieurs éléments (identiques) dans une liste

avec enumerate(alist) vous pouvez stocker le premier élément (n) Qui est l'index de la liste lorsque l'élément x est égal à ce que vous recherchez.

>>> alist = ['foo', 'spam', 'egg', 'foo']
>>> foo_indexes = [n for n,x in enumerate(alist) if x=='foo']
>>> foo_indexes
[0, 3]
>>>

faisons notre fonction findindex

Cette fonction prend l'élément et la liste des arguments et retourne la position de l'élément dans la liste, comme nous l'avons vu avant.

def indexlist(item2find, list_or_string):
  "Returns all indexes of an item in a list or a string"
  return [n for n,item in enumerate(list_or_string) if item==item2find]

print(indexlist("1", "010101010"))

Sortie


[1, 3, 5, 7]

Simple

for n, i in enumerate([1, 2, 3, 4, 1]):
    if i == 1:
        print(n)

sortie:

0
4
12
répondu Giovanni Gianni 2018-06-04 23:28:43
la source

Cette solution n'est pas aussi puissante que d'autres, mais si vous êtes un débutant et que vous ne connaissez que les boucles for , il est encore possible de trouver le premier index d'un article tout en évitant L'erreur de valeur:

def find_element(p,t):
    i = 0
    for e in p:
        if e == t:
            return i
        else:
            i +=1
    return -1
9
répondu dylankb 2017-11-12 09:07:52
la source
name ="bar"
list = [["foo", 1], ["bar", 2], ["baz", 3]]
new_list=[]
for item in list:
    new_list.append(item[0])
print(new_list)
try:
    location= new_list.index(name)
except:
    location=-1
print (location)

, Ce qui représente si la chaîne n'est pas dans la liste, si elle n'est pas dans la liste puis l'emplacement = -1

5
répondu Coder123 2015-07-05 16:12:19
la source

étant donné que les listes Python sont basées sur zéro, nous pouvons utiliser la fonction zip intégrée comme suit:

>>> [i for i,j in zip(range(len(haystack)), haystack) if j == 'needle' ]

où "botte de foin" est la liste en question, et "aiguille" est l'élément à rechercher.

(Note: ici nous itérons en utilisant i pour obtenir les index, mais si nous avons besoin plutôt de se concentrer sur les éléments nous pouvons passer à J.)

5
répondu jihed gasmi 2018-06-04 23:56:33
la source

il y a une réponse plus fonctionnelle à cela.

list(filter(lambda x: x[1]=="bar",enumerate(["foo", "bar", "baz", "bar", "baz", "bar", "a", "b", "c"])))

forme plus générique:

def get_index_of(lst, element):
    return list(map(lambda x: x[0],\
       (list(filter(lambda x: x[1]==element, enumerate(lst))))))
3
répondu Ankit Gupta 2018-06-04 23:53:01
la source

Python index() méthode lance une erreur si l'objet n'a pas été trouvé, ce qui craint!

donc vous pouvez le faire similaire à la fonction indexOf() de JavaScript qui retourne -1 si l'article n'a pas été trouvé:

    try:
        index = array.index('search_keyword')
    except ValueError:
        index = -1
3
répondu Hamed Baatour 2018-06-04 23:53:55
la source

Trouver l'indice de l'élément x dans la liste L :

idx = L.index(x) if (x in L) else -1
2
répondu Ketan 2018-06-01 01:46:51
la source

pour ceux qui viennent d'une autre langue comme moi, peut-être qu'avec une simple boucle c'est plus facile à comprendre et à utiliser:

mylist = ["foo", "bar", "baz", "bar"]
newlist = enumerate(mylist)
for index, item in newlist:
  if item == "bar":
    print(index, item)

je suis reconnaissant pour alors que fait exactement enumerate? . Qui m'a aidé à comprendre.

1
répondu mpoletto 2018-06-04 23:55:15
la source

si la performance est préoccupante:

il est mentionné dans de nombreuses réponses que la méthode intégrée de list.index(item) est un algorithme O(n). Il est très bien si vous avez besoin d'effectuer cette fois. Mais si vous avez besoin d'accéder aux indices d'éléments un certain nombre de fois, il est plus logique de créer d'abord un dictionnaire (O(n)) de paires d'éléments-index, puis accéder à l'index à O(1) chaque fois que vous en avez besoin.

Si vous êtes sûr que les articles dans votre liste ne sont jamais répétés, vous pouvez facilement:

myList = ["foo", "bar", "baz"]

# Create the dictionary
myDict = dict((e,i) for i,e in enumerate(myList))

# Lookup
myDict["bar"] # Returns 1
# myDict.get("blah") if you don't want an error to be raised if element not found.

si vous avez des éléments en double, et avez besoin de retourner tous leurs indices:

from collections import defaultdict as dd
myList = ["foo", "bar", "bar", "baz", "foo"]

# Create the dictionary
myDict = dd(list)
for i,e in enumerate(myList):
    myDict[e].append(i)

# Lookup
myDict["foo"] # Returns [0, 4]
1
répondu FatihAkici 2018-09-10 21:51:04
la source

il y a deux possibilités si la liste n'a pas d'éléments répétés que vous devez vérifier l'index pour

 eg: li=[10,20,30] # here need to get index of 20 means
     li.index(20) # will work properly because 20 is not repeated

si son moyen répété signifie qu'il vous donnera seulement le premier index

si vous devez obtenir tout l'index où l'élément est présent signifie

eg: li=[10,20,30,20,40, 50, 10] # here need to get index of 20 means its have 2 index (1,3) 

pour obtenir que vous avez besoin de le faire comme

 li=[10,20,30,20,40, 50, 10]
 [i for i, e in enumerate(li) if e == 20]

alors vous obtiendrez une liste d'index comme O/p comme [1,3]

1
répondu abhi krishnan 2018-10-04 08:26:17
la source

comme indiqué par @TerryA, beaucoup de réponses discutent comment trouver un index.

more_itertools est une bibliothèque de tiers avec des outils pour localiser multiple indices dans un itérable.

Donné

import more_itertools as mit


iterable = ["foo", "bar", "baz", "ham", "foo", "bar", "baz"]

Code

trouver des indices d'observations multiples:

list(mit.locate(iterable, lambda x: x == "bar"))
# [1, 5]

Test de plusieurs éléments:

list(mit.locate(iterable, lambda x: x in {"bar", "ham"}))
# [1, 3, 5]

voir aussi plus d'options avec more_itertools.locate . Installer via > pip install more_itertools .

0
répondu pylang 2018-09-25 18:47:56
la source

Autres questions sur python list