Per raccogliere solo un elemento di un utilizzo generatore break
in una dichiarazione for
, o list(itertools.islice(gen, 1))
Secondo il vostro esempio (letteralmente) si può fare come:
while True:
...
if something:
for my_element in myfunct():
dostuff(my_element)
break
else:
do_generator_empty()
Se si vuole "get jus t un elemento dal [una volta generate] generatore ogni volta mi piace "(suppongo il 50% questo è l'intenzione originale, e l'intenzione più comune), allora:
gen = myfunct()
while True:
...
if something:
for my_element in gen:
dostuff(my_element)
break
else:
do_generator_empty()
In questo modo l'uso esplicito di generator.next()
può essere evitato e la gestione di fine input non richiede (criptica) la gestione delle eccezioni StopIteration
o confronti di valori di default aggiuntivi.
La sezione di istruzioni else:
di for
è necessaria solo se si desidera fare qualcosa di speciale in caso di fine del generatore.
Note on next()
/.next()
:
Nel python3 metodo .next()
è stato rinominato .__next__()
per una buona ragione: la sua considerata di basso livello (PEP 3114). Prima di Python 2.6 la funzione incorporata next()
non esisteva. Ed è stato anche discusso di spostare next()
nel modulo operator
(che sarebbe stato saggio), a causa della sua rara necessità e dell'inflazione discutibile dei nomi di costruzione.
L'utilizzo di next()
senza impostazione predefinita è ancora una pratica di livello molto basso - lanciando il criptico StopIteration
come un fulmine fuori dal blu nel normale codice di applicazione apertamente. E usando next()
con sentinella di default - quale migliore dovrebbe essere l'unica opzione per un next()
direttamente in builtins
- è limitato e spesso dà ragione a strane logiche/leggibilità non-pythonic.
Linea inferiore: l'utilizzo di next() dovrebbe essere molto raro, ad esempio utilizzando le funzioni del modulo operator
. L'utilizzo di for x in iterator
, islice
, list(iterator)
e altre funzioni che accettano senza problemi un iteratore è il modo naturale di utilizzare gli iteratori a livello di applicazione, e tutto ciò è sempre possibile. next()
è di basso livello, un concetto in più, non ovvio - come mostra la domanda di questo thread. Ad esempio, ad es. utilizzando break
in for
è convenzionale.
Nota, solleverà StopIteration solo quando si tenta di utilizzare g.next() dopo che è stato fornito l'ultimo elemento in g. – Wilduck
'next (gen, default)' può anche essere usato per evitare l'eccezione 'StopIteration'. Ad esempio "next (g, None)" per un generatore di stringhe produrrà una stringa o None dopo che l'iterazione è stata completata. – Attila
in Python 3000, next() è __next __() –