how to correctly modify the iterator of a loop in python from within the loop

后端 未结 4 1578
清酒与你
清酒与你 2021-02-08 11:37

what I basically need is to check every element of a list and if some criteria fit I want to remove it from the list.

So for example let\'s say that

list         


        
相关标签:
4条回答
  • 2021-02-08 12:16

    If you are ok with creating a copy of the list you can do it like this (list comprehension):

    [s for s in list if s != 'b' and s != 'c']
    
    0 讨论(0)
  • 2021-02-08 12:18

    Its better not to reinvent things which are already available. Use filter functions and lambda in these cases. Its more pythonic and looks cleaner.

    filter(lambda x:x not in ['b','c'],['a','b','c','d','e'])
    

    alternatively you can use list comprehension

    [x for x in ['a','b','c','d','e'] if x not in ['b','c']]
    
    0 讨论(0)
  • 2021-02-08 12:35

    The easier way is to use a copy of the list - it can be done with a slice that extends "from the beginning" to the "end" of the list, like this:

    for s in list[:]:
        if s=='b' or s=='c':
            list.remove(s)
    

    You have considered this, and this is simple enough to be in your code, unless this list is really big, and in a critical part of the code (like, in the main loop of an action game). In that case, I sometimes use the following idiom:

    to_remove = []
    for index, s in enumerate(list):
        if s == "b" or s == "c":
             to_remove.append(index)
    
    for index in reversed(to_remove):
        del list[index]
    

    Of course you can resort to a while loop instead:

    index = 0
    while index < len(list):
       if s == "b" or s == "c":
           del list[index]
           continue
       index += 1
    
    0 讨论(0)
  • 2021-02-08 12:37

    This is exactly what itertools.ifilter is designed for.

    from itertools import ifilter
    
    ifilter(lambda x: x not in ['b', 'c'], ['a', 'b', 'c', 'd', 'e'])
    

    will give you back a generator for your list. If you actually need a list, you can create it using one of the standard techniques for converting a generator to a list:

    list(ifilter(lambda x: x not in ['b', 'c'], ['a', 'b', 'c', 'd', 'e']))
    

    or

    [x for x in ifilter(lambda x: x not in ['b', 'c'], ['a', 'b', 'c', 'd', 'e'])]
    
    0 讨论(0)
提交回复
热议问题