ИЛИ поведение в питоне:

1

Я написал следующий фрагмент кода, все, что я хочу сделать, это напечатать "да", если число передано строковым представлением 1, 0 или 2, а для всего остального - false:

number=raw_input()
if number is "1" or "0" or "2":
    print "Yes"
else:
     print "no"

Я знаю, как заставить предполагаемую логику работать, но мне просто нужно знать, почему она печатает "да" для любого числа, которое я передаю в raw_input. Я бы хотел, чтобы ответ был настолько подробным, насколько это возможно, потому что я не могу понять, почему он потерпит неудачу, мне кажется, что это достаточно pythonic

Теги:

3 ответа

4
Лучший ответ

Проблема в том, что ваш код для Python читается следующим образом:

if (number is "1") or "0" or "2":

И поскольку любая непустая строка оценивает значение True, она всегда True.

Чтобы сделать то, что вы хотите сделать, хороший синтаксис:

if number in {"1", "0", "2"}:

Обратите внимание на мое использование набора здесь - в то время как в этом случае это не имеет большого значения (только с тремя значениями), проверка по набору выполняется быстрее, чем список, поскольку тест на членство для набора равен O (1) вместо O (п).

Это проще и проще писать:

if number == "1" or number == "0" or number == "2":

Это то, что вы хотели.

Обратите внимание, что при сопоставлении значения вы всегда должны использовать == not is - is - проверка идентичности (два значения - один и тот же объект). Обычно вы должны использовать is для таких вещей, как is True или is None.

Если вы хотите обрабатывать это как число, вы можете сделать что-то вроде этого:

try:
   value = int(number)
except ValueError:
   value = None
if value is not None and 0 <= value <= 2:
    ...

Что может быть более полезным в ситуациях, когда вы хотите сравнить с большим количеством чисел. Обратите внимание на то, что я использую полезную цепочку сравнения Python (0 <= value <= 2 а не 0 <= value and value <= 2).

  • 0
    +1 для заданного литерала (доступно в Python 2.7+), а также предупреждение о сравнении строк с использованием is .
  • 0
    Спасибо ... особенно за примечание в конце, я не знал этого.
2

Правильный синтаксис выглядит следующим образом:

if number == "1" or number == "0" or number == "2":
    print "Yes"

Или более Pythonic:

if number in ["1", "2", "3"]:
    print "Yes"

Или вы можете применить к int и попробовать:

if int(number) in range(1,4):
    print "Yes"

Причина, по которой ваш код оценивает значение " True - это все время, потому что он оценивает истину "0" и "2", что, как утверждения, истинно в Python.

  • 0
    Обратите внимание, что использование списка для этого является плохой идеей - хотя в этом случае с небольшим набором проверок это не имеет большого значения, проверка на членство в списке выполняется медленнее, поэтому имеет смысл использовать наборы. Также стоит отметить, что ваш последний пример будет генерировать исключения, если входные данные могут быть чем-то, что не является числом.
  • 0
    Я знал о возможном исключении, но не о снижении производительности при проверке членства в списке. Спасибо за чаевые!
0

Потому что каждое выражение между or оценивается как логическое выражение.

if True оценивает значение True, if 1: оценивает значение True, if "0": значение True.

Итак, то, что вы написали, более или менее эквивалентно:

if number is "1":
    print "Yes"
elif "0":
    print "Yes"
elif "2":
    print "Yes"
else:
     print "no"

Вы должны были бы написать, if number is "1" or number is "0" or number "2": или более pythonic: if number in ("1", "0", "2"):

Ещё вопросы

Сообщество Overcoder
Наверх
Меню