Manchmal muss ich eine Liste in Python iterieren und dabei das "aktuelle" Element und das "nächste" Element betrachten. Ich habe dies bis jetzt mit Code wie: getan.
for current, next in zip(the_list, the_list[1:]):
# Do something
Dies funktioniert und macht das, was ich erwarte, aber gibt es eine idiomatischere oder effizientere Möglichkeit, dasselbe zu tun?
next
diese Weise ein eingebautes maskiert wird.next
ist auch eine in Python 2Antworten:
Hier ist ein relevantes Beispiel aus den Dokumenten des itertools- Moduls:
Für Python 2 benötigen Sie
itertools.izip
anstelle vonzip
:So funktioniert das:
Zuerst werden zwei parallel Iteratoren,
a
undb
werden erstellt (dertee()
Anruf), die beide nach dem ersten Element des ursprünglichen iterable. Der zweite Iteratorb
wird 1 Schritt vorwärts (dernext(b, None)
Aufruf) verschoben . An dieser Stellea
zeigt auf s0 undb
zeigt auf s1. Beidea
undb
können den ursprünglichen Iterator unabhängig voneinander durchlaufen - die izip-Funktion verwendet die beiden Iteratoren und erstellt Paare der zurückgegebenen Elemente, wobei beide Iteratoren im gleichen Tempo weiterentwickelt werden.Eine Einschränkung: Die
tee()
Funktion erzeugt zwei Iteratoren, die unabhängig voneinander vorrücken können, jedoch mit Kosten verbunden sind. Wenn einer der Iteratoren weiter voranschreitet als der andere,tee()
müssen die verbrauchten Elemente im Speicher bleiben, bis der zweite Iterator sie ebenfalls verbraucht (der ursprüngliche Iterator kann nicht zurückgespult werden). Hier spielt es keine Rolle, da ein Iterator dem anderen nur einen Schritt voraus ist, aber im Allgemeinen ist es einfach, auf diese Weise viel Speicher zu verwenden.Und da
tee()
einn
Parameter verwendet werden kann, kann dieser auch für mehr als zwei parallele Iteratoren verwendet werden:quelle
zip(ł, ł[1:])
ist viel kürzer und pythonischfuncy
Modul:funcy.pairwise
: funcy.readthedocs.io/en/stable/seqs.html#pairwiseRoll deinen eigenen!
quelle
Da
the_list[1:]
tatsächlich eine Kopie der gesamten Liste (mit Ausnahme des ersten Elements) erstellt wird undzip()
beim Aufruf sofort eine Liste der Tupel erstellt wird, werden insgesamt drei Kopien Ihrer Liste erstellt. Wenn Ihre Liste sehr groß ist, bevorzugen Sie vielleichtdas kopiert die Liste überhaupt nicht.
quelle
the_list[1:]
nur ein Slice-Objekt erstellt, sondern eine Kopie fast der gesamten Liste. Die Technik des OP ist also nicht ganz so verschwenderisch, wie Sie es klingen lassen.[1:]
erstellt das Slice-Objekt (oder möglicherweise "1:
"), das in__slice__
der Liste übergeben wird, und gibt dann eine Kopie zurück, die nur die ausgewählten Elemente enthält. Eine idiomatische Art, eine Liste zu kopieren, istl_copy = l[:]
(was ich hässlich und unlesbar finde - lieberl_copy = list(l)
)__slice__
spezielle Methode.the_list[1:]
ist äquivalent zuthe_list[slice(1, None)]
, was wiederum äquivalent zu istlist.__getitem__(the_list, slice(1, None))
.the_list[1:]
ist nur eine flache Kopie, daher besteht sie nur aus einem Zeiger pro Listenelement. Der speicherintensivere Teil ist derzip()
selbst, da eine Liste mit einertuple
Instanz pro Listenelement erstellt wird, die jeweils zwei Zeiger auf die beiden Elemente und einige zusätzliche Informationen enthält. Diese Liste belegt das Neunfache des Speichers, den die Kopie[1:]
verbraucht.Ich lösche das nur, ich bin sehr überrascht, dass niemand daran gedacht hat, aufzuzählen ().
quelle
if
kann das auch entfernt werden, wenn Sie das Schneiden verwenden:for (index, thing) in enumerate(the_list[:-1]): current, next_ = thing, the_list[index + 1]
Das Iterieren nach Index kann dasselbe bewirken:
Ausgabe:
quelle
i
immer der Index des aktuellen Elements angezeigt wird.Dies ist jetzt ein einfacher Import ab dem 16. Mai 2020
Dokumente für mehr itertools Unter der Haube ist dieser Code der gleiche wie in den anderen Antworten, aber ich bevorzuge Importe, wenn verfügbar.
Wenn Sie es noch nicht installiert haben, dann:
pip install more-itertools
Beispiel
Wenn Sie beispielsweise die Fibbonnacci-Sequenz hätten, könnten Sie die Verhältnisse nachfolgender Paare wie folgt berechnen:
quelle
Paare aus einer Liste unter Verwendung eines Listenverständnisses
Ausgabe:
quelle
Ich bin wirklich überrascht, dass niemand die kürzere, einfachere und vor allem allgemeine Lösung erwähnt hat:
Python 3:
Python 2:
Es funktioniert für die paarweise Iteration durch Übergeben
n=2
, kann jedoch jede höhere Zahl verarbeiten:quelle
Eine grundlegende Lösung:
quelle
quelle