Skip to content

Instantly share code, notes, and snippets.

@alexlouden
Last active December 19, 2022 15:19
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save alexlouden/9f1ab4354d1c68ae4c1c94126ac51a20 to your computer and use it in GitHub Desktop.
Save alexlouden/9f1ab4354d1c68ae4c1c94126ac51a20 to your computer and use it in GitHub Desktop.

First, let's try just iterating through the list as we delete:

Here we're trying to remove all the numbers in our list under 3.

mylist = [1, 2, 3, 4, 5]

for item in mylist:
    if item < 3:
        mylist.remove(item)

print(mylist)
# [2, 3, 4, 5]

You can see that 2 is still in the list, because we were iterating over the list while we deleted elements from it.

If we modify our example above and add print(mylist, item) inside the loop, we get the following output:

[1, 2, 3, 4, 5] 1
[2, 3, 4, 5] 3
[2, 3, 4, 5] 4
[2, 3, 4, 5] 5

You can see item jumps from 1 to 3 - that's because the iterator went from the first index (1) to the second index (which was 2, but by the second loop it turned into 3).

If we iterate over a copy of the list instead:

mylist = [1, 2, 3, 4, 5]

for item in mylist[:]:
    if item < 3:
        mylist.remove(item)
      
print(mylist)
# [3, 4, 5]

Since item iterates through the copy of the list, we can safely delete from mylist as we iterate.

A more pythonic approach

Another option is to create a whole new list, rather than modify mylist. I'd typically use a list comprehension like this for small lists:

mylist = [1, 2, 3, 4, 5]

mynewlist = [item for item in mylist if item >= 3]

print(mynewlist)
[3, 4, 5]

My example from StackOverflow, modified to delete either "c" or "d":

a = ["a", "b", "c", "d", "e"]

for item in a:
    print(item)
    if item == "b" or item == "c":
        a.remove(item)

# a
# b
# d
# e

print(a)
# ['a', 'c', 'd', 'e']
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment