Ich entwickle gerade ein Programm in Python und habe gerade bemerkt, dass etwas mit der foreach-Schleife in der Sprache oder vielleicht der Listenstruktur nicht stimmt. Ich werde nur ein generisches Beispiel meines Problems zur Vereinfachung geben, da ich das gleiche fehlerhafte Verhalten sowohl in meinem Programm als auch in meinem generischen Beispiel bekomme:
%Vor%Nun, das Problem hier ist einfach, ich dachte, dass dieser Code alle Elemente aus einer Liste entfernen sollte. Nun, das Problem ist, dass ich nach der Ausführung immer 2 Elemente in der Liste bekomme.
Was mache ich falsch? Danke für die Hilfe im Voraus.
Bearbeiten: Ich möchte keine Liste leeren, dies ist nur ein Beispiel ...
Dies ist ein gut dokumentiertes Verhalten in Python, dass Sie die Liste, die durchlaufen wird, nicht ändern sollten. Versuchen Sie es stattdessen:
%Vor% Das [:]
gibt ein "Segment" von x
zurück, das zufällig alle seine Elemente enthält und somit eine Kopie von x
ist.
Ich denke, im Großen und Ganzen, wenn Sie schreiben:
%Vor%Unter der Haube macht Python so etwas:
%Vor% Wenn Sie lst.remove(x)
für den Schleifenkörper einfügen, können Sie dann vielleicht sehen, warum Sie das Ergebnis erhalten, das Sie tun?
Im Wesentlichen verwendet Python einen beweglichen Zeiger, um die Liste zu durchlaufen. Der Zeiger beginnt mit dem Zeigen auf das erste Element. Dann entfernen Sie das erste Element und machen das zweite Element zum neuen ersten Element. Dann bewegt sich der Zeiger zum neuen zweiten - vorher dritten - Element. Und so weiter. (Es könnte klarer sein, wenn Sie [1,2,3,4,5] anstelle von [1,2,2,2,2] als Beispielliste verwenden)
Ich stimme John Fouhy bezüglich der Unterbrechungsbedingung zu. Das Durchlaufen einer Kopie der Liste funktioniert für die Methode remove (), wie Chris Jester-Young vorgeschlagen hat. Aber wenn man bestimmte Elemente poppen () muss, funktioniert das Iterieren in umgekehrter Reihenfolge, wie Erik erwähnte, in welchem Fall die Operation an Ort und Stelle durchgeführt werden kann. Zum Beispiel:
%Vor%
oder mit xrange:
Ich weiß, das ist ein alter Post mit einer akzeptierten Antwort, aber für diejenigen, die vielleicht noch kommen ...
Einige frühere Antworten haben gezeigt, dass es eine schlechte Idee ist, während der Iteration eine Iteration zu ändern. Aber um zu zeigen, was passiert ...
%Vor%Hoffentlich hilft das Visuelle zu klären.