Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

This is something that's bothered me for a while, and I can't figure out why anyone would ever want the language to act like this:

In [1]: foo = [1, 2, 3]

In [2]: foo.remove(2) ; foo  # okay
Out[2]: [1, 3]

In [3]: foo.remove(4) ; foo  # not okay?
---------------------------------------------------------------------------
ValueError                                Traceback (most recent call last)

/home/izkata/<ipython console> in <module>()

ValueError: list.remove(x): x not in list

If the value is already not in the list, then I'd expect a silent success. Goal already achieved. Is there any real reason this was done this way? It forces awkward code that should be much shorter:

for item in items_to_remove:
   try:
      thingamabob.remove(item)
   except ValueError:
      pass

Instead of simply:

for item in items_to_remove:
   thingamabob.remove(item)

As an aside, no, I can't just use set(thingamabob).difference(items_to_remove) because I do have to retain both order and duplicates.

share|improve this question
    
If you want silent success you can use del instead. –  faif Sep 21 '12 at 15:56
    
@faif del foo[foo.index(4)] -> ValueError: list.index(x): x not in list. Even if I already had a possible index, del foo[4] -> IndexError: list assignment index out of range. del is just as bad as .remove() –  Izkata Sep 21 '12 at 16:48
    
You're right. It seems that there's no way to "silently" remove an item from a list. You can use a list comprehension though: [x.remove(i) for i in x[:] if i in y] –  faif Sep 21 '12 at 18:22
add comment

2 Answers 2

From the Python philosophy:

Explicit is better than implicit

The .remove() method has raised an exception from the very first commit; trying to remove a value that is not there gives you explicit feedback instead of implicitly assuming that the value not being there was fine and what you wanted all along.

share|improve this answer
    
Okay. So why is it useful? Just a theoretical from Python's beginnings that was never revisited? –  Izkata Sep 21 '12 at 16:50
    
No, some use-cases require you to know if the item is not there when removing. It could indicate a bug, for example. Just because your use-case could be simpler without the exception doesn't mean everyone else has the same use-cases. :-) –  Martijn Pieters Sep 21 '12 at 16:54
    
Also, Python has been around for over 20 years. Every single decision in the language has been revisited by now. –  Martijn Pieters Sep 21 '12 at 16:55
add comment

As an aside: unless your list is extremely large and the list of items to remove is excessively small in comparison, you can create a new list with the items excluded in one readable line:

filtered_list = [x for x in source_list if x not in set(items_to_remove)]

Obviously it preserves order and duplicates as you want. Very probably it is also faster.

Very often not mutating data greatly simplifies the way you think about an algorithm.

share|improve this answer
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.