Как проверить, есть ли что-то (нет) в списке в Python?
Самое дешевое и удобочитаемое решение - использование inоператора (или в вашем конкретном случае not in). Как указано в документации,
Операторы inи not inтест на членство. x in sоценивается,
Trueесли xявляется членом s, и в Falseпротивном случае. x not in sвозвращает отрицание x in s.
Дополнительно,
Оператор not inопределен, чтобы иметь обратное истинное значение in.
y not in xлогически так же, как not y in x.
Вот несколько примеров:
'a' in [1, 2, 3]
# False
'c' in ['a', 'b', 'c']
# True
'a' not in [1, 2, 3]
# True
'c' not in ['a', 'b', 'c']
# False
Это также работает с кортежами, так как кортежи являются хэшируемыми (вследствие того, что они также являются неизменяемыми):
(1, 2) in [(3, 4), (1, 2)]
# True
Если объект в RHS определяет __contains__()метод, он inбудет внутренне вызывать его, как указано в последнем абзаце раздела « Сравнения » документации.
... inи not inподдерживаются типами, которые являются итеративными или реализуют
__contains__()метод. Например, вы можете (но не должны) сделать это:
[3, 2, 1].__contains__(1)
# True
inкороткие замыкания, поэтому, если ваш элемент находится в начале списка, inвычисляется быстрее:
lst = list(range(10001))
%timeit 1 in lst
%timeit 10000 in lst # Expected to take longer time.
68.9 ns ± 0.613 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)
178 µs ± 5.01 µs per loop (mean ± std. dev. of 7 runs, 10000 loops each)
Если вы хотите сделать больше, чем просто проверить, есть ли элемент в списке, есть варианты:
list.indexможет быть использован для получения индекса элемента. Если этот элемент не существует, a ValueErrorповышается.
list.count может быть использован, если вы хотите подсчитать вхождения.
Проблема XY: Вы рассматривали setс?
Задайте себе эти вопросы:
- Вам нужно проверить, есть ли элемент в списке более одного раза?
- Эта проверка выполняется внутри цикла или функция вызывается повторно?
- Элементы, которые вы храните в своем списке, можно изменить? IOW, вы можете позвонить
hashим?
Если вы ответили «да» на эти вопросы, вы должны использовать setвместо этого. Проверка inчленства на lists - это O (n) сложность времени. Это означает, что python должен выполнить линейное сканирование вашего списка, посещая каждый элемент и сравнивая его с элементом поиска. Если вы делаете это неоднократно или если списки велики, эта операция повлечет за собой дополнительные затраты.
setобъекты, с другой стороны, хэшируют свои значения для проверки членства в постоянное время. Проверка также выполняется с использованием in:
1 in {1, 2, 3}
# True
'a' not in {'a', 'b', 'c'}
# False
(1, 2) in {('a', 'c'), (1, 2)}
# True
Если вам не повезло, что элемент, который вы ищете / не ищете, находится в конце вашего списка, python просканирует список до конца. Это видно из времени ниже:
l = list(range(100001))
s = set(l)
%timeit 100000 in l
%timeit 100000 in s
2.58 ms ± 58.9 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
101 ns ± 9.53 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)
Напоминаем, что это подходящий вариант, если элементы, которые вы храните и просматриваете, являются хэшируемыми. Таким образом, они должны быть неизменяемыми типами или объектами, которые реализуют __hash__.
3 -1 > 0 and (4-1 , 5) not in []⤇Trueпоэтому ошибка не является одним из приоритетов операторов.