Encontrar el índice de un artículo en una lista


3186

Dada una lista ["foo", "bar", "baz"]y un elemento en la lista "bar", ¿cómo obtengo su index ( 1) en Python?


66
¿Está regresando: [1] El índice más bajo en caso de que haya varias instancias de "bar", [2] Todos los índices de "bar"?
Ṃųỻịgǻňạcểơửṩ

44
a) ¿Se garantiza que el elemento está en la lista o, de lo contrario, cómo debemos manejar el caso de error? (return None / raise ValueError) b) ¿Se garantiza que las entradas de la lista sean únicas, y debemos devolver el primer índice de una coincidencia o todos los índices?
smci

Vea las respuestas con una integración numpy, las matrices numpy son mucho más eficientes que las listas de Python. Si la lista es corta, no hay problema para hacer una copia de ella desde una lista de Python, si no lo es, tal vez debería considerar almacenar los elementos en una matriz numpy en primer lugar.
Athanassios

Respuestas:


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

Referencia: Estructuras de datos> Más sobre listas

Siguen las advertencias

Tenga en cuenta que si bien esta es quizás la forma más limpia de responder a la pregunta que se le hizo , indexes un componente bastante débil de la listAPI, y no puedo recordar la última vez que lo usé con ira. Se me ha señalado en los comentarios que debido a que esta respuesta está muy referenciada, debería hacerse más completa. Algunas advertencias sobre list.indexseguir. Probablemente valga la pena echarle un vistazo a la documentación:

list.index(x[, start[, end]])

Devuelve el índice basado en cero en la lista del primer elemento cuyo valor es igual a x . Aumenta un ValueErrorsi no hay tal artículo.

Los argumentos opcionales start y end se interpretan como en la notación de corte y se usan para limitar la búsqueda a una subsecuencia particular de la lista. El índice devuelto se calcula en relación con el comienzo de la secuencia completa en lugar del argumento de inicio.

Complejidad lineal del tiempo en la longitud de la lista

Una indexllamada verifica cada elemento de la lista en orden, hasta que encuentra una coincidencia. Si su lista es larga y no sabe aproximadamente en qué parte de la lista ocurre, esta búsqueda podría convertirse en un cuello de botella. En ese caso, debe considerar una estructura de datos diferente. Tenga en cuenta que si sabe aproximadamente dónde encontrar la coincidencia, puede dar indexuna pista. Por ejemplo, en este fragmento, l.index(999_999, 999_990, 1_000_000)es aproximadamente cinco órdenes de magnitud más rápido que directo l.index(999_999), porque el primero solo tiene que buscar 10 entradas, mientras que el segundo busca un millón:

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

Solo devuelve el índice del primer partido a su argumento

Una llamada para indexbuscar en la lista en orden hasta que encuentre una coincidencia y se detiene allí. Si espera necesitar índices de más coincidencias, debe utilizar una lista de comprensión o expresión generadora.

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

En la mayoría de los lugares donde alguna vez lo hubiera usado index, ahora uso una lista de comprensión o expresión generadora porque son más generalizables. Entonces, si está considerando alcanzarlo index, eche un vistazo a estas excelentes características de Python.

Lanza si el elemento no está presente en la lista

Una llamada a indexresulta en un ValueErrorsi el elemento no está presente.

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

Si el elemento puede no estar presente en la lista, debe

  1. Verifíquelo primero con item in my_list(enfoque limpio y legible), o
  2. Envuelva la indexllamada en un try/exceptbloque que atrapa ValueError(probablemente más rápido, al menos cuando la lista para buscar es larga y el elemento generalmente está presente).

20
index devuelve el primer elemento cuyo valor es "bar". Si la "barra" existe dos veces en la lista, nunca encontrará la clave para la segunda "barra". Ver documentación: docs.python.org/3/tutorial/datastructures.html
mpoletto

2
Si solo está buscando un elemento (el primero), descubrí que index()es un 90% más rápido que la comprensión de listas con listas de enteros.
slybloty

¿Qué estructura de datos se debe usar si la lista es muy larga?
izhang05

@izhang: Algunos índices auxiliares, como un dictado {element -> list_index}, si los elementos son hashaable, y la posición en la lista es importante.
Alex Coventry

899

Una cosa que es realmente útil para aprender Python es usar la función de ayuda interactiva:

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

class list(object)
 ...

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

que a menudo lo llevará al método que está buscando.


2
bpython es una forma agradable y fácil de usar para leer los documentos de manera interactiva.
goetzc

@davidavr sí, pero el resto de nosotros que solo queremos buscarlo en Google en lugar de desplazarnos por los documentos de ayuda no tendríamos este conjunto de opciones agradable, central y clasificado. :)
honkaboy

556

La mayoría de las respuestas explican cómo encontrar un índice único , pero sus métodos no devuelven índices múltiples si el elemento está en la lista varias veces. Uso enumerate():

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

La index()función solo devuelve la primera aparición, mientras queenumerate() devuelve todas las ocurrencias.

Como una lista de comprensión:

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

Aquí también hay otra pequeña solución con itertools.count()(que es más o menos el mismo enfoque que enumerar):

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

Esto es más eficiente para listas más grandes que usar 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

La enumeración funciona mejor que los métodos basados ​​en índices para mí, ya que estoy buscando recopilar los índices de cadenas usando 'beginwith ", y necesito reunir múltiples ocurrencias. ¿O hay una manera de usar index con" beginwith "que yo no podía entender
Tupelo Thistlehead

3
En mis manos, la versión de enumerar es consistentemente un poco más rápida. Algunos detalles de implementación pueden haber cambiado desde que se publicó la medición anterior.
Alex Coventry

2
Esto ya fue respondido desde '11: stackoverflow.com/questions/6294179/…
Cristik


132

index()devuelve el primer índice de valor!

El | índice (...)
| L.index (valor, [inicio, [detener]]) -> entero - devuelve el primer índice de valor

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"])

2
¿Y si no existe en la lista?
Peter Mortensen

1
El elemento inexistente aumentará ValueError
Nam G VU

1
Esta respuesta encajaría mejor aquí: stackoverflow.com/questions/6294179/…
Cristik

86

Surgirá un problema si el elemento no está en la lista. Esta función maneja el problema:

# 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


58

Debe establecer una condición para verificar si el elemento que está buscando está en la lista

if 'your_element' in mylist:
    print mylist.index('your_element')
else:
    print None

1
¡Esto nos ayuda a evitar intentar atrapar!
devssh

Sin embargo, podría duplicar la complejidad. ¿Alguien lo comprobó?
stefanct

@stefanct La complejidad del tiempo sigue siendo lineal, pero recorrerá la lista dos veces.
ApproachingDarknessFish

@ApproachingDarknessFish Eso es obviamente lo que quise decir. Incluso si pedagógicamente es el mismo orden de complejidad, iterar dos veces podría ser una grave desventaja en muchos casos de uso, así que lo mencioné. Y todavía no sabemos la respuesta ...
stefanct

44

Todas las funciones propuestas aquí reproducen el comportamiento inherente del lenguaje pero ocultan lo que está sucediendo.

[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

¿Por qué escribir una función con manejo de excepciones si el lenguaje proporciona los métodos para hacer lo que quieres?


99
El tercer método itera dos veces sobre la lista, ¿verdad?
Eric Duminil

Re: "Todas las funciones propuestas aquí" : tal vez al momento de escribir, pero debe verificar las respuestas más recientes para ver si aún es cierto.
Peter Mortensen

41

Si desea todos los índices, puede usar 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),)

Es una solución clara y legible.


44
¿Qué pasa con las listas de cadenas, listas de objetos no numéricos, etc.?
Laryx Decidua

1
Esta respuesta debería publicarse mejor aquí: stackoverflow.com/questions/6294179/…
Cristik

1
Este es el mejor que he leído. Las matrices numpy son mucho más eficientes que las listas de Python. Si la lista es corta, no hay problema en hacer una copia de ella desde una lista de Python, si no lo es, tal vez el desarrollador debería considerar almacenar los elementos en una matriz numpy en primer lugar.
Athanassios

35

Encontrar el índice de un elemento dada una lista que lo contiene en Python

Para una lista ["foo", "bar", "baz"]y un elemento en la lista "bar", ¿cuál es la forma más limpia de obtener su índice (1) en Python?

Bueno, claro, está el método de índice, que devuelve el índice de la primera aparición:

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

Hay un par de problemas con este método:

  • si el valor no está en la lista, obtendrá un ValueError
  • Si hay más de uno de los valores en la lista, solo obtendrá el índice para el primero

Sin valores

Si el valor puede faltar, debe capturar el ValueError.

Puede hacerlo con una definición reutilizable como esta:

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

Y úsalo así:

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

Y la desventaja de esto es que probablemente verifique si el valor devuelto iso is notNinguno:

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

Más de un valor en la lista.

Si pudiera tener más casos, no obtendrá información completa con list.index:

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

Puede enumerar en una lista la comprensión de los índices:

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

Si no tiene ocurrencias, puede verificarlo con una verificación booleana del resultado, o simplemente no hacer nada si recorre los resultados:

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

Mejor mezcla de datos con pandas

Si tiene pandas, puede obtener fácilmente esta información con un objeto Serie:

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

Una verificación de comparación devolverá una serie de booleanos:

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

Pase esa serie de booleanos a la serie mediante notación de subíndice, y obtendrá solo los miembros coincidentes:

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

Si solo desea los índices, el atributo index devuelve una serie de enteros:

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

Y si los quiere en una lista o tupla, simplemente páselos al constructor:

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

Sí, también podría usar una comprensión de lista con enumerate, pero eso no es tan elegante, en mi opinión: está haciendo pruebas de igualdad en Python, en lugar de dejar que el código incorporado escrito en C lo maneje:

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

¿Es este un problema XY ?

El problema XY es preguntar acerca de su intento de solución en lugar de su problema real.

¿Por qué crees que necesitas el índice dado un elemento en una lista?

Si ya conoce el valor, ¿por qué le importa dónde está en una lista?

Si el valor no está allí, la captura ValueErrores bastante detallada, y prefiero evitar eso.

Por lo general, estoy iterando sobre la lista de todos modos, por lo que generalmente mantendré un puntero a cualquier información interesante, obteniendo el índice con enumerate.

Si está mezclando datos, probablemente debería usar pandas, que tiene herramientas mucho más elegantes que las soluciones puras de Python que he mostrado.

No recuerdo haberlo necesitado list.index. Sin embargo, he examinado la biblioteca estándar de Python y veo algunos usos excelentes para ella.

Hay muchos, muchos usos para ello idlelib, para GUI y análisis de texto.

El keywordmódulo lo utiliza para buscar marcadores de comentarios en el módulo para regenerar automáticamente la lista de palabras clave a través de metaprogramación.

En Lib / box.py parece estar usándolo como una asignación ordenada:

key_list[key_list.index(old)] = new

y

del key_list[key_list.index(key)]

En Lib / http / cookiejar.py, parece usarse para obtener el próximo mes:

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

En Lib / tarfile.py similar a distutils para obtener un corte hasta un elemento:

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

En Lib / pickletools.py:

numtopop = before.index(markobject)

Lo que estos usos parecen tener en común es que parecen operar en listas de tamaños restringidos (importante debido al tiempo de búsqueda de O (n) para list.index ), y se usan principalmente en el análisis (y la IU en el caso de Idle).

Si bien hay casos de uso, son bastante poco comunes. Si se encuentra buscando esta respuesta, pregúntese si lo que está haciendo es el uso más directo de las herramientas proporcionadas por el idioma para su caso de uso.



21

Obtener todas las ocurrencias y la posición de uno o más elementos (idénticos) en una lista

Con enumerate (alist) puede almacenar el primer elemento (n) que es el índice de la lista cuando el elemento x es igual a lo que busca.

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

Hagamos que nuestra función encuentre index

Esta función toma el elemento y la lista como argumentos y devuelve la posición del elemento en la lista, como vimos antes.

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

Salida


[1, 3, 5, 7]

Simple

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

Salida:

0
4

1
Esta respuesta debería publicarse mejor aquí: stackoverflow.com/questions/6294179/…
Cristik

16

Simplemente puedes ir con

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

res = [[x[0] for x in a].index(y) for y in b]


15

Y ahora para algo completamente diferente...

... como confirmar la existencia del artículo antes de obtener el índice. Lo bueno de este enfoque es que la función siempre devuelve una lista de índices, incluso si es una lista vacía. Funciona con cadenas también.

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

Cuando se pega en una ventana interactiva de Python:

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

Actualizar

Después de otro año de desarrollo de Python, estoy un poco avergonzado por mi respuesta original, por lo que para dejar las cosas claras, uno ciertamente puede usar el código anterior; sin embargo, la forma mucho más idiomática de obtener el mismo comportamiento sería usar la comprensión de la lista, junto con la función enumerate ().

Algo como esto:

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

Que, cuando se pega en una ventana interactiva de Python produce:

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

Y ahora, después de revisar esta pregunta y todas las respuestas, me doy cuenta de que esto es exactamente lo que FMc sugirió en su respuesta anterior . En el momento en que originalmente respondí esta pregunta, ni siquiera vi esa respuesta, porque no la entendí. Espero que mi ejemplo un poco más detallado ayude a comprender.

Si la única línea de código anterior aún no tiene sentido para usted, le recomiendo encarecidamente la 'comprensión de la lista de python' de Google y tome unos minutos para familiarizarse. Es solo una de las muchas características poderosas que hacen que sea un placer usar Python para desarrollar código.


12

Una variante en la respuesta de FMc y user7177 dará un dict que puede devolver todos los índices para cualquier entrada:

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

También puede usar esto como una línea para obtener todos los índices para una sola entrada. No hay garantías de eficiencia, aunque utilicé el set (a) para reducir la cantidad de veces que se llama al lambda.


1
Esta respuesta debería publicarse mejor aquí: stackoverflow.com/questions/6294179/…
Cristik

10

Esta solución no es tan poderosa como otras, pero si eres un principiante y solo conoces los forbucles, aún es posible encontrar el primer índice de un elemento mientras evitas el ValueError:

def find_element(p,t):
    i = 0
    for e in p:
        if e == t:
            return i
        else:
            i +=1
    return -1

9

Encontrar el índice del elemento x en la lista L:

idx = L.index(x) if (x in L) else -1

44
Esto itera la matriz dos veces, por lo que podría ocasionar problemas de rendimiento para matrices grandes.
Cristik

De acuerdo. Si las listas son considerablemente largas, iría por otra cosa. Sin embargo, no debería ser un gran problema para las listas de tamaño pequeño a mediano.
Ketan

5

Como las listas de Python están basadas en cero, podemos usar la función integrada zip de la siguiente manera:

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

donde "pajar" es la lista en cuestión y "aguja" es el elemento a buscar.

(Nota: Aquí estamos iterando usando i para obtener los índices, pero si necesitamos centrarnos en los elementos, podemos cambiar a j.)


3
[i para i, j en enumerate (haystack) si j == 'aguja'] es más compacto y legible, creo.
Giovanni G. PY

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

Esto explica si la cadena no está en la lista también, si no está en la lista, entonces location = -1


4

El index()método Python arroja un error si no se encontró el elemento. Por lo tanto, puede hacerlo similar a la indexOf()función de JavaScript que se devuelve -1si no se encuentra el elemento:

try:
    index = array.index('search_keyword')
except ValueError:
    index = -1

55
sin embargo, JavaScript tiene la filosofía de que los resultados extraños son mejores que los errores, por lo que tiene sentido devolver -1, pero en Python, puede ser difícil rastrear un error, ya que -1 devuelve un elemento desde el final de la lista.
Sapphire_Brick

3

Hay una respuesta más funcional a esto.

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

Forma más genérica:

def get_index_of(lst, element):
    return list(map(lambda x: x[0],\
       (list(filter(lambda x: x[1]==element, enumerate(lst))))))

1
Esta respuesta se siente en casa para Scala/ de programación funcionales entusiastas
y2k-shubham

3

Démosle el nombre lsta la lista que tiene. Uno puede convertir la lista lsta a numpy array. Y luego use numpy.where para obtener el índice del elemento elegido en la lista. A continuación se detalla la forma en que lo implementará.

import numpy as np

lst = ["foo", "bar", "baz"]  #lst: : 'list' data type
print np.where( np.array(lst) == 'bar')[0][0]

>>> 1

2

Para aquellos que vienen de otro idioma como yo, tal vez con un bucle simple es más fácil de entender y usar:

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

Estoy agradecido por ¿Qué hace exactamente enumerar? . Eso me ayudó a entender.


2

Si va a encontrar un índice una vez, entonces usar el método "index" está bien. Sin embargo, si va a buscar sus datos más de una vez, le recomiendo usar el módulo bisect . Tenga en cuenta que el uso de datos de módulo bisecado debe ordenarse. Entonces ordena los datos una vez y luego puede usar bisect. Usando bisectos módulo en mi máquina es aproximadamente 20 veces más rápido que usar el método index.

Aquí hay un ejemplo de código que usa Python 3.8 y la sintaxis anterior:

import bisect
from timeit import timeit

def bisect_search(container, value):
    return (
      index 
      if (index := bisect.bisect_left(container, value)) < len(container) 
      and container[index] == value else -1
    )

data = list(range(1000))
# value to search
value = 666

# times to test
ttt = 1000

t1 = timeit(lambda: data.index(value), number=ttt)
t2 = timeit(lambda: bisect_search(data, value), number=ttt)

print(f"{t1=:.4f}, {t2=:.4f}, diffs {t1/t2=:.2f}")

Salida:

t1=0.0400, t2=0.0020, diffs t1/t2=19.60

1

Si el rendimiento es preocupante:

En numerosas respuestas se menciona que el método incorporado de list.index(item) método es un algoritmo O (n). Está bien si necesita realizar esto una vez. Pero si necesita acceder a los índices de elementos varias veces, tiene más sentido crear primero un diccionario (O (n)) de pares de ítems-índice y luego acceder al índice en O (1) cada vez que lo necesite eso.

Si está seguro de que los elementos de su lista nunca se repiten, puede:

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 puede tener elementos duplicados y necesita devolver todos sus índices:

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

Como lo indica @TerryA, muchas respuestas discuten cómo encontrar un índice.

more_itertoolses una biblioteca de terceros con herramientas para localizar múltiples índices dentro de un iterable.

Dado

import more_itertools as mit


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

Código

Encuentra índices de múltiples observaciones:

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

Prueba múltiples artículos:

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

Ver también más opciones con more_itertools.locate. Instalar a través de > pip install more_itertools.


0

usando el diccionario, donde procesa la lista primero y luego agrega el índice

from collections import defaultdict

index_dict = defaultdict(list)    
word_list =  ['foo','bar','baz','bar','any', 'foo', 'much']

for word_index in range(len(word_list)) :
    index_dict[word_list[word_index]].append(word_index)

word_index_to_find = 'foo'       
print(index_dict[word_index_to_find])

# output :  [0, 5]

-1

en mi opinión, ["foo", "bar", "baz"].index("bar")es bueno, ¡pero no es suficiente! porque si "bar" no está en el diccionario, se ValueErroreleva . Entonces puede usar esta función:

def find_index(arr, name):
    try:
        return arr.index(name)
    except ValueError:
        return -1

if __name__ == '__main__':
    print(find_index(["foo", "bar", "baz"], "bar"))

y el resultado es:

1

y si name no estaba en arr, la función return -1.por ejemplo:

print (find_index (["foo", "bar", "baz"], "fooo"))

-1


1
No use esto porque l = [1, 2]; find_index(l, 3)regresaría -1y l[find_index(l, 3)]regresaría 2. -1 es algo malo para devolver, solo devuelve None.
Daniel Stracaboško

-1 es un contrato que puede devolver lo que quiera Pero intente utilizar None menor en sus programas porque None o Null en la comunicación de su programa con otros programas como sitios web de Android y PHP pueden causar interrupción del programa, por ejemplo, puede devolver nulo en JSON y la aplicación de teléfono de su sitio web se cerrará o devolverá el Error 500 (error interno del servidor).
NaabNuts
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.