список и подсписок python

Я должен проверить, содержится ли список1 в списке2. Он также должен проверить, отображается ли он в этом порядке в списке. Если это правда, он должен вернуть true и false, если это не так.

def check(lst1, lst2):
for x in lst1:
    for y in lst2:
        xx = lst1.sort()
        yy = lst2
        if xx != yy:
            return False
        else:
            return True

Я запутался в циклах for, а также не знаю, куда идти дальше, чтобы исправить свой код. Указатели, пожалуйста?

пример того, что он должен делать:

  check([4,0],[9,1,4,6,8,9])
  True
  check([1,2],[2,3,1])
  False

person 97834657647563    schedule 28.02.2011    source источник
comment
В вашем примере, почему первая проверка возвращает True? Ноль не во втором списке.   -  person yan    schedule 01.03.2011
comment
Если список1 должен содержаться по порядку в списке2, не потеряете ли вы порядок при сортировке()?   -  person payne    schedule 01.03.2011
comment
Зачем вам зацикливаться на двух списках, если вы никогда не используете элементы x и y в теле цикла?   -  person Wang    schedule 01.03.2011


Ответы (3)


Я думал, что проблема требует рекурсивного решения, поэтому я сделал:

def check(needle, haystack):
  if not needle:
      return True
  try:
    offset = haystack.index(needle[0])
    return check(needle[1:], haystack[offset+1:])
  except:
    return False

Редактировать:

Краткое объяснение:

Сначала мы проверяем, является ли искомый список пустым (это важно, когда мы начинаем вызывать себя), так как все списки содержат внутри себя пустой список, мы возвращаем True. Затем мы пытаемся найти первый элемент списка, который мы ищем, в списке, который мы просматриваем. Если находим, то снова вызываем функцию, но немного меняем аргументы: мы уже смотрели на первый предмет «иголки» и видели его в «стоге сена». Итак, теперь нам нужно проверить, находится ли остаток «иглы» в остатке «стога сена». Поэтому мы снова вызываем функцию только с оставшейся частью обоих списков. Остаток от иглы — это все, кроме первого элемента, а остаток от стога сена — все элементы после найденного. Если мы доходим до точки, где первый список пуст, значит, мы нашли его в стоге сена. Если мы получаем исключение, то, что мы искали, не было найдено, поэтому мы возвращаем False, который всплывает в стеке вызовов и возвращается.

person yan    schedule 28.02.2011
comment
index возвращает индекс искомого элемента, а Python использует полуоткрытые интервалы, поэтому стог сена[смещение:] не удалит искомый элемент из стога сена. - person Wang; 01.03.2011
comment
Спасибо, было очень легко понять! - person 97834657647563; 01.03.2011
comment
Подождите, нет, слишком рано сказал, я пытался взять этот код в качестве модели для себя. Затем, как только я добрался до «вернуть чек (игла [1:], стог сена [смещение + 1:])», я полностью запутался. Объяснение? Извините, я новичок в python. - person 97834657647563; 01.03.2011
comment
Я понимаю, что это просто странный/неожиданный вопрос... Я надеялся, что это будет False: check([1,2,3], [1,1,2,2,3,3]), то есть подсписок. - person Andy Hayden; 19.11.2014

Вы можете начать с чего-то вроде:

set(lst1).issubset(lst2)

чтобы увидеть, содержится ли lst1 в lst2, игнорируя порядок. Если он проходит тест на то, что один список содержится в другом, вы можете сделать что-то вроде:

ii = lst2.index(lst1[0])
if lst2[ii:ii+len(lst1)] == lst1:
   return True
else:
   return False

Первоначально я заявил, что первая проверка не имеет значения, учитывая вторую, хотя вам придется правильно обрабатывать ValueError, если первый элемент lst1 не находится в lst2.

Редактировать: В качестве примечания я сравнил свою версию кода с версией yan, и моя версия значительно быстрее почти во всех случаях использования, особенно если len(lst1) больше (ускорение до 200x по сравнению с yan). реализация). Попробуйте с модулем timeit.

def check(lst1,lst2):
    try:
        ii = lst2.index(lst1[0])
    except ValueError:
        return False

    if lst2[ii:ii+len(lst1)] == lst1:
        return True
    else:
        return False 

В качестве объяснения того, как это работает, ii = lst2.index(lst1[0]) находит индекс в lst2, который соответствует первому элементу lst1. Если этот элемент отсутствует в lst2, он перехватывает ValueError и возвращает False. Если этот элемент существует, lst2[ii:ii+len(lst1)] == lst1 сравнивает все lst1 с подсписком lst2, начиная с совпавшего элемента и беря следующие len(lst) элементов.

person JoshAdel    schedule 28.02.2011
comment
Ваше решение меня заинтриговало, особенно эта строка: if lst2[ii:ii+len(lst1)] == lst1:. Вы не против объяснить это мне? - person 97834657647563; 01.03.2011
comment
добавлена ​​фактическая реализация и объяснение - person JoshAdel; 01.03.2011
comment
Ваш ответ может быть быстрее, чем алгоритм Яна, но это потому, что он неверен. Вы предполагаете, что элементы в lst1 идут последовательно в lst2. yan’s — традиционный алгоритм решения этой задачи. - person user176121; 16.02.2012

person    schedule
comment
Я считаю, что проблема OP может включать случаи, когда элементы искомого списка не являются последовательными в искомом списке. Кроме того, не уверен, что указана длина два. - person yan; 01.03.2011
comment
@yan Конечно, я подумал, что покажу, как решить один случай, и ОП может обобщить его, как им нравится. - person Matt Curtis; 01.03.2011
comment
@OP: вы можете вызвать zip с более чем двумя списками, поэтому, чтобы получить by_three, вы можете сделать zip(a, a[1:], a[2:]) ... - person Matt Curtis; 01.03.2011