Search code examples
pythonpython-2.7string-search

Remove last occurrence of element containing substring from a list


So say I have, list1 = ['the dog', 'the cat', 'cat dog', 'the dog ran home']

and sub_string = 'the dog'

how can I return list2 = ['the dog', 'the cat', 'cat dog']

i.e, return a list with the last occurrence of the substring removed?


Solution

  • No built-in will help much you here, since scanning for a substring in a list isn't a supported feature, and doing so in reverse order is doubly hard. List comprehensions won't do much good either, since making them stateful enough to recognize when you've found your needle would involve adding side-effects to the list comprehension, which makes it cryptic and violates the purpose of functional programming tools. So you're stuck doing the looping yourself:

    list2 = []
    list1iter = reversed(list1)  # Make a reverse iterator over list1
    for item in list1iter:
        if sub_string in item:   # Found item to remove, don't append it, we're done
            break
        list2.append(item)       # Haven't found it yet, keep item
    list2.extend(list1iter)      # Pull all items after removed item
    list2.reverse()              # Put result back in forward order
    

    Try it online!

    An alternative approach would be to scan by index, allowing you to del it; this might be a better solution if you want to modify list1 in place, rather than making a new list:

    for i, item in enumerate(reversed(list1), 1):
        if sub_string in item:
            del list1[-i]
            break
    

    Try it online!

    That solution is adaptable to making a new copy by simply changing all references to list1 to list2, and adding list2 = list1[:] before the loop.

    In both cases, you can detect if an item was found at all by putting an else: block on the for; if the else block triggers, you didn't break, because sub_string wasn't found anywhere.