que - Manera más limpia de obtener el último elemento del iterador de Python
python funciones generadoras (11)
¿Cuál es la mejor manera de obtener el último elemento de un iterador en Python 2.6? Por ejemplo, di
my_iter = iter(range(5))
¿Cuál es el modo más corto / más limpio de obtener 4
de my_iter
?
Podría hacer esto, pero no parece muy eficiente:
[x for x in my_iter][-1]
Es poco probable que sea más rápido que el ciclo vacío debido a la lambda, pero tal vez le dará a alguien más una idea
reduce(lambda x,y:y,my_iter)
Si el iter está vacío, se genera un TypeError
Hay esto
list( the_iter )[-1]
Si la duración de la iteración es verdaderamente épica, tanto tiempo que la materialización de la lista agota la memoria, entonces realmente necesita replantearse el diseño.
La pregunta es incorrecta y solo puede conducir a una respuesta que es complicada e ineficiente. Para obtener un iterador, por supuesto comienza desde algo iterable, que en la mayoría de los casos ofrece una forma más directa de acceder al último elemento.
Una vez que crea un iterador a partir de un iterable, se ve atrapado al pasar por los elementos, porque eso es lo único que ofrece un iterable.
Entonces, la forma más eficiente y clara es no crear el iterador en primer lugar, sino usar los métodos de acceso nativos del iterable.
Probablemente valga la pena usar __reversed__
si está disponible
if hasattr(my_iter,''__reversed__''):
last = next(reversed(my_iter))
else:
for last in my_iter:
pass
Si está utilizando Python 3.x:
*_, last = iterator # for a better understanding check PEP 448
print(last)
si está utilizando Python 2.7:
last = next(iterator)
for last in iterator:
continue
print last
Solo usaría next(reversed(myiter))
Tan simple como:
max(enumerate(the_iter))[1]
Usaría el reversed
, excepto que solo toma secuencias en lugar de iteradores, lo que parece bastante arbitrario.
De cualquier forma que lo hagas, tendrás que ejecutar todo el iterador. Con la máxima eficiencia, si no necesita el iterador nunca más, puede destruir todos los valores:
for last in my_iter:
pass
# last is now the last item
Creo que esta es una solución subóptima, sin embargo.
Use una deque
de tamaño 1.
from collections import deque
#aa is an interator
aa = iter(''apple'')
dd = deque(aa, maxlen=1)
last_element = dd.pop()
Vea este código para algo similar:
http://excamera.com/sphinx/article-islast.html
puede usarlo para recoger el último artículo con:
[(last, e) for (last, e) in islast(the_iter) if last]
item = defaultvalue
for item in my_iter:
pass