Search code examples
pythonlistboolean-logic

What's wrong with this list comprehension?


I have listA=[[0,1],[1,2]], and listB=[[0,1,2],[0,1,3],[0,2,3],[0,2,4]]. I want to find all elements b from listB such that b⊆a doesn't hold and a⊆b doesn't hold for all elements a from listA. Put it another way, my desired output is: listC=[[0,2,3],[0,2,4]].

I tried the following codes:

import numpy as np

listA=[[0,1],[1,2]]
listB=[[0,1,2],[0,1,3],[0,2,3],[0,2,4]]

listC=[b for b in listB if (((not set(a).issubset(set(b))) and (not set(b).issubset(set(a)))) for a in listA)]
print(listC)

However, the output is [[0,1,2],[0,1,3],[0,2,3],[0,2,4]], which is not what I want. My guess is that something is wrong in the if part of the list comprehension. How could it be fixed? Thanks.


Solution

  • Your condition is a little wonky. You want the elements in listB that are not superset (or subset) of any element in listA. So if you replace

    (((not set(a).issubset(set(b))) and (not set(b).issubset(set(a)))) for a in listA)
    

    with

    any(set(a).issubset(b) or set(b).issubset(a) for a in listA)
    

    it will work as expected.

    listC = [b for b in listB if not any(set(a).issubset(b) or set(b).issubset(a) for a in listA)]
    

    Output:

    [[0, 2, 3], [0, 2, 4]]