2008-11-14 7 views
29

me gustaría hacer algo como:filtrar una lista de Python predicado

>>> lst = [1, 2, 3, 4, 5] 
>>> lst.find(lambda x: x % 2 == 0) 
2 
>>> lst.findall(lambda x: x % 2 == 0) 
[2, 4] 

¿Hay algo acerca a este tipo de comportamiento en las bibliotecas estándar de Python?

Sé que es muy fácil rodar por cuenta propia aquí, pero estoy buscando una forma más estándar.

Respuesta

46

Se puede utilizar el método de filtro:


>>> lst = [1, 2, 3, 4, 5] 
>>> filter(lambda x: x % 2 == 0, lst) 
[2, 4] 

o una lista por comprensión:


>>> lst = [1, 2, 3, 4, 5] 
>>> [x for x in lst if x %2 == 0] 
[2, 4] 

EDIT: para find (solo elemento), usted podría intentar:


>>> (x for x in lst if x % 2 == 0).next() 
2 

Aunque eso arrojaría una excepción si nada coincide, por lo que probablemente quieras envolverlo en un try/catch. Los corchetes() hacen de esto una expresión generadora en lugar de una lista de comprensión.

Personalmente, yo solo usaría el filtro/comprensión habitual y tomaría el primer elemento (si hay alguno).

Estos lanzar una excepción si no se encuentra nada

filter(lambda x: x % 2 == 0, lst)[0] 
[x for x in lst if x %2 == 0][0] 

Estos valores vuelven listas vacías

filter(lambda x: x % 2 == 0, lst)[:1] 
[x for x in lst if x %2 == 0][:1] 
+1

Gracias! Eso es para findall. ¿Qué hay de encontrar? –

+1

En lugar de una comprensión de generador, también puede usar itertools.ifilter (func, list) .next() que está un poco más cerca de la sintaxis deseada. – Brian

+3

También puede usar itertools.dropwhile (lambda x: not func (x), list) que no arrojará una excepción si la lista no contiene ningún elemento que satisfaga el predicado. También tiene la ventaja de que puede provocar un cortocircuito si el elemento deseado se produce antes del final de la lista. – EfForEffort

Cuestiones relacionadas