как узнать, есть ли значение в списке, которое находится между двумя значениями из другого списка

#python #list #bisect

#python #Список #разделить пополам

Вопрос:

У меня есть два списка

 a = [1, 4, 12]
b = [2, 13]
  

Я хочу знать, находятся ли значения в list b между двумя значениями в list a
Итак, в этом случае 2 будет находиться между 1 и 4. 13 не будет находиться между никакими числами.

Я пробовал bisect function, но не смог заставить его работать. Я смог использовать его с одним значением и списком, но не с двумя списками.

Комментарии:

1. В приведенном выше случае вы хотите, чтобы вывод был [True, False]

2. Между любыми двумя числами или между числами, которые следуют друг за другом или непосредственно друг за другом? Отсортирован ли первый список? И вы ищете только да / нет или фактические числа и / или их позицию в списке? Должны ли все значения in b находиться между одинаковыми числами из a , или они независимы?

3. @SidKwakkel да, True, False будет работать

4. @tobias_k два списка независимы — между двумя числами не может быть никакого значения. Кроме того, предположим, что два списка отсортированы.

5. Кроме того, означает ли «между», что числа должны быть строго меньше и меньше, чем те, которые они «между»? А как насчет границ? Будет 1 4 ли и 12 быть «между» любыми числами a ?

Ответ №1:

Возможно, есть какая-то тонкость, которую я не понимаю, но, если я не ошибаюсь, вам нужно только проверить, находятся ли элементы между min и max from a . Это не зависит от того, отсортированы ли элементы в a , или значения из b должны быть между последовательными значениями из a . Пока они находятся между min и max , в этих значениях должен a быть «сегмент».

 >>> a = [1, 4, 12]
>>> b = [2, 13]
>>> n, m = min(a), max(a)
>>> [n < x < m for x in b]
[True, False]
  

Это, конечно, только в том случае, если (а) вам не нужно, какие числа они находятся между ними, и (б) если не все значения в b должны быть в одном и том же интервале.

Если вы считаете, что я что-то пропустил, пожалуйста, прокомментируйте.

Комментарии:

1. подождите, это правильно! как мы это пропустили. Кроме (a) того, указанный вами пункт на самом деле не является недостатком. Должно работать в [x for x in b if n < x < m] любом случае.

2. Одно из возможных предостережений: если «между» действительно означает n < x < m , то может не быть никакого интервала, в котором числа b находятся «между», если список a «плотный», например 3 , не находится между какими-либо числами [1,2,3,4,5] .

3. я предполагаю, что a и be никогда не будут иметь одинаковое число. если 3 находится в списке A, то B никогда не будет содержать 3

Ответ №2:

Это действительно зависит от того, что вы хотите, чтобы оно вернуло. Я написал код, который вернет первый найденный шаблон, но с некоторыми изменениями, я уверен, будет нетрудно вернуть все комбинации.

 def get_between(a, b):
    a, b = sorted(a), sorted(b)
    
    for b_value in b:
        smaller = None
        greater = None
        for a_value in a:
            if b_value > a_value:
                smaller = a_value
            elif b_value < a_value:
                greater = a_value
            
            if smaller and greater:
                return f"{b_value} is between {smaller} and {greater}"
    
    return "There is no such combination"

a = [1, 4, 12]
b = [2, 13]
print(get_between(a, b))
  

Вывод в этом случае будет 2 is between 1 and 4 , но вы можете адаптировать возвращаемое значение к тому, что вы хотите.

Ответ №3:

Вы можете сохранить два запущенных индекса, чтобы получить список всех элементов, которые находятся между значениями:

 def get_between(arr1, arr2):
    # first sort the arrays
    arr1 = sorted(arr1)
    arr2 = sorted(arr2)
    # keep two indices into them
    i1 = 0
    i2 = 0
    # keep track of the values between two values
    ret = []
    while i1 < len(arr1) - 1 and i2 < len(arr2):
        # we're too small to be between a value
        # so we should increase the second index
        if arr2[i2] < arr1[i1]:
            i2  = 1
        # we're too large to be between a value
        # so we should increase the first index
        elif arr2[i2] > arr1[i1   1]:
            i1  = 1
        # we are between a value
        # so we should append to the return array
        # and move on to the next element
        else:
            ret.append(arr2[i2])
            i2  = 1
    return ret

get_between([1, 4, 12], [2, 8, 13]) # [2, 8]
  

Ответ №4:

Если вы не очень заботитесь о производительности, вот решение pythonic-

 def betwn(rangelist, valuelist):
    # Get list of all ranges between each consecutive number of rangelist
    rgs = [range(rangelist[n], rangelist[n   1]) for n in range(len(rangelist) - 1)]
    # A function to check whether a given element exists between 2 consecutive numbers of rangelist
    verifyfunc = lambda e: any(e in r for r in rgs)
    # Return the qualifying elements from valuelist
    return [e for e in valuelist if verifyfunc(e)]
  

Вывод

 >>> betwn([1, 4, 12], [2, 13])
[2]