Mutating a list during iteration invalidates the iterator's internal index
A Python list iterator stores an internal index that advances by one on each next() call. When you remove or insert elements during iteration, the list shifts, but the iterator's index does not adjust. So the iterator can skip elements, revisit elements, or run past the end. The result is that the loop silently processes the wrong items or raises IndexError. The safe patterns are to iterate over a copy (for x in list(lst)), build a new list with a comprehension, or collect indices to delete and remove them after the loop. In Python 3, list iterators are not designed to detect mutation, so there is no error; you just get wrong behavior.
Removing an element shifts subsequent items left, so the iterator's next index skips the item that moved into the removed slot.
Appending during iteration can cause an infinite loop because the iterator keeps finding new elements.
Iterate over a copy when you must mutate: for x in lst[:] or for x in list(lst).
Use a list comprehension to build a new list: lst = [x for x in lst if condition].
Common mistake: assuming Python will raise an error when you mutate during iteration. It does not.
Common mistake: using remove() inside a for loop over the same list, which skips elements.
Version note: this behavior is consistent across Python 3 versions; it is a consequence of the iterator protocol.
0-2 years experience
2-5 years experience
5-8 years experience
8+ years experience