chodzi o to, co rzeczywiście wydarzyło się w dla pętli:
ZPython for statement documentation:
The lista wyrażeń jest oceniana raz; powinien dać obiekt iterowalny . Iterator jest tworzony dla wyniku expression_list
. Pakiet jest następnie wykonywany po dla każdej pozycji dostarczonej przez iterator , w porządku rosnących indeksów. Każdy element z kolei jest przypisany do listy docelowej z listą przy użyciu standardowych reguł dla przydziałów, , a następnie pakiet jest wykonywany. Gdy elementy są wyczerpane (co jest natychmiast, gdy sekwencja jest pusty), apartament w klauzuli else
, jeżeli występuje, jest wykonywane, a loop
kończy.
Myślę, że najlepiej pokazać za pomocą ilustracji .
Teraz załóżmy, że masz iterable object
(takich jak list
) tak:
out = [a, b, c, d, e, f]
Co się stanie, gdy robisz for x in out
jest to, że tworzy wewnętrzną podziałowe który wygląda tak (ja zilustrować go z symbol ^
):
[a, b, c, d, e, f]
^ <-- here is the indexer
Co zwykle się zdarzyć, że: jak zakończyć jeden cykl swojej pętli, przesuwa Indexer przekazania takiego:
[a, b, c, d, e, f] #cycle 1
^ <-- here is the indexer
[a, b, c, d, e, f] #cycle 2
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 3
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 4
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 5
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 6
^<-- here is the indexer
#finish, no element is found anymore!
Jak widać, urządzenie podziałowe utrzymuje naprzód do końca listy , niezależnie od tego, co się stało z listy!
Zatem kiedy robisz remove
, to co się wewnętrznie:
[a, b, c, d, e, f] #cycle 1
^ <-- here is the indexer
[b, c, d, e, f] #cycle 1 - a is removed!
^ <-- here is the indexer
[b, c, d, e, f] #cycle 2
^<-- here is the indexer
[c, d, e, f] #cycle 2 - c is removed
^<-- here is the indexer
[c, d, e, f] #cycle 3
^<-- here is the indexer
[c, d, f] #cycle 3 - e is removed
^<-- here is the indexer
#the for loop ends
Zauważ, że istnieją tylko 3 cykle tam zamiast 6 cykli (!!) (która jest liczbą elementów z pierwotnej listy). Dlatego właśnie pozostawiłeś półlen
z oryginalnego len
, ponieważ jest to liczba cykli wymaganych do ukończenia pętli po usunięciu z niej jednego elementu dla każdego cyklu.
Jeśli chcesz wyczyścić listę, po prostu zrobić:
if (out != []):
out.clear()
albo, alternatywnie, aby usunąć element, jeden po drugim, trzeba to zrobić na odwrót - od koniec do początku. Użyj reversed
:
for x in reversed(out):
out.remove(x)
Teraz, to dlaczego praca reversed
? Jeśli indeksator będzie posuwał się naprzód, czy nie powinien również działać reversed
, ponieważ numer elementu jest w każdym razie zmniejszony o jeden na cykl?
Nie, to nie jest tak,
Ponieważ reversed
metoda zmienia drogę do wewnętrznego indekser dzieła! To, co się stało podczas używania metody reversed
, to: , aby wewnętrzny indeksator przesuwał się w tył (od końca) zamiast naprzód.
Aby zilustrować, to jest to, co zwykle się dzieje:
[a, b, c, d, e, f] #cycle 1
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 2
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 3
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 4
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 5
^<-- here is the indexer
[a, b, c, d, e, f] #cycle 6
^ <-- here is the indexer
#finish, no element is found anymore!
I tak, kiedy wykonujesz jedno usunięcie w cyklu, to nie ma wpływu na sposób indeksowania działa:
[a, b, c, d, e, f] #cycle 1
^<-- here is the indexer
[a, b, c, d, e] #cycle 1 - f is removed
^<-- here is the indexer
[a, b, c, d, e] #cycle 2
^<-- here is the indexer
[a, b, c, d] #cycle 2 - e is removed
^<-- here is the indexer
[a, b, c, d] #cycle 3
^<-- here is the indexer
[a, b, c] #cycle 3 - d is removed
^<-- here is the indexer
[a, b, c] #cycle 4
^<-- here is the indexer
[a, b] #cycle 4 - c is removed
^<-- here is the indexer
[a, b] #cycle 5
^<-- here is the indexer
[a] #cycle 5 - b is removed
^<-- here is the indexer
[a] #cycle 6
^ <-- here is the indexer
[] #cycle 6 - a is removed
^ <-- here is the indexer
Nadzieja ilustracja pomaga zrozumieć, co się dzieje wewnętrznie ...
"Wtedy próbuję usunąć wszystko z listy" - zagłębimy się tutaj głębiej. Dlaczego chcesz to zrobić? –
Ponieważ przenoszę wartości z listy do słownika w parach, tak jak pierwsza wartość w parze to klucz, a druga jako wartość. Chodzi o to, że mój słownik jest niekompletny, ponieważ nie mogę go w pełni przejrzeć - mówi, że istnieje tylko 96 indeksów. – user4447655
Jeśli możesz opublikować kod za pomocą napisu i dyktatu, którego używasz, łatwiej nam będzie zaproponować rozwiązanie. Problem może być inny niż to, co nam dałeś do tej pory. – MKreegs