-2

I have a list of lists, consisting of only numbers, with two numbers for each nested list which represent start and end offsets: x = [[54, 61], [254, 275], [298, 314], [350, 362], [387, 391], [457, 472]]

and then a list of two numbers e.g. y = [54,67] . I would like filter x so that it doesn't contain complete or partial matches, depending on y.

For example if y = [54,67], then the output would be x = [[254, 275], [298, 314], [350, 362], [387, 391], [457, 472]] because [54,61] is entailed in [54,67]. Other examples of partial matches for this x would be

y = [54,61]
x = [[298, 314], [350, 362], [387, 391], [457, 472]]

y = [253,275]
x = [[54, 61], [298, 314], [350, 362], [387, 391], [457, 472]]

y =  [290, 315]
x = [[54, 61], [254, 275], [350, 362], [387, 391], [457, 472]]

y =  [351, 361]
x = [[54, 61], [254, 275], [298, 314], [387, 391], [457, 472]]

What I have been trying is to match either the first of the second elements, but I don't know how to go about the partial ones.

y = [54, 61]
x = [[54, 67], [254, 275], [298, 314], [350, 362], [387, 391], [457, 472]]
out = [i for i in x if (i[0] or i[1]) not in y]
Pranav Hosangadi
  • 23,755
  • 7
  • 44
  • 70
Paschalis
  • 191
  • 10
  • What do you mean by entailment? I am not familiar with this term. Specifically, I don't understand why for example `[290, 315]` matches `[298, 314]. – zr0gravity7 Jan 05 '22 at 17:05
  • `(i[0] or i[1]) not in y` is not the correct way to check that `y` contains neither element of `i`. See a similar question [here](/q/15112125) and [here](/q/20002503) – Pranav Hosangadi Jan 05 '22 at 17:15
  • 1
    Maybe I used the term too freely. It does not match it exactly, but the range between 298 and 314 is entailed in the range between 290 and 315 – Paschalis Jan 05 '22 at 17:16
  • 1
    In fact, it looks like you don't even want to check that `y` contains neither element of `i`. You want to check that `y[0] <= i[0] and y[1] >= i[1]` – Pranav Hosangadi Jan 05 '22 at 17:20

1 Answers1

0

As other people commented, I also found the requirement a bit confusing.

If I understood the requirements correctly: given the range in y, you don't want any of the list items in x to overlap at all.

The thing to note is definitely how you're defining your list comprehension and how you're doing your logical checks.

In example below, the list is built to make sure neither end point in i is within the end points in y:

out = [
    i for i in x
    if (i[0] < y[0] and i[1] < y[0])  # i[0] and i[1] are less than y[0]
    or (i[0] > y[1] and i[1] > y[1])  # i[0] and i[1] are greater than y[1]
]

Starting with x = [[54, 61], [254, 275], [298, 314], [350, 362], [387, 391], [457, 472]]

Below are different values for y and the corresponding outputs:

with y = [54, 61]

Note: In your example above, you didn't include [254, 275]. I assume that is a typo.

[[254, 275], [298, 314], [350, 362], [387, 391], [457, 472]]

with y = [253, 275]

[[54, 61], [298, 314], [350, 362], [387, 391], [457, 472]]

with y = [290, 315]

[[54, 61], [254, 275], [350, 362], [387, 391], [457, 472]]

with y = [351, 361]

[[54, 61], [254, 275], [298, 314], [387, 391], [457, 472]]
Jorge Gx
  • 311
  • 3
  • 13