not None тест в Python [дублировать]
Вопрос
На этот вопрос уже есть ответ здесь:
Из этих тестов нет ни одного.
if val != None:
if not (val is None):
if val is not None:
Какой из них предпочтительнее и почему?
Решение
if val is not None:
# ...
является ли Pythonic идиомой для проверки того, что переменная не установлена в значение None
.Эта идиома имеет особое применение в случае объявление функций ключевого слова с параметрами по умолчанию. is
проверяет идентичность в Python.Потому что существует один-единственный экземпляр None
присутствует в запущенном скрипте / программе Python, is
является оптимальным тестом для этого.Как Johnsyweb указывает на, это обсуждается в БОДРОСТЬ ДУХА 8 в разделе "Рекомендации по программированию".
Что касается того, почему это предпочтительнее
if not (val is None):
# ...
это просто часть Дзен питона:"Важна читаемость". Хороший Python часто близок к хорошему псевдокод.
Другие советы
Из рекомендаций программирования, Pep 8.:
Сравнение людей, таких как никто не всегда должен быть сделан с «IS» или «не», никогда не являются операторами равенства.
Кроме того, остерегайтесь написания «Если X», когда вы действительно имеете в виду «если X нет ничего» - например, при тестировании, является ли переменная или аргумент, которые значение по умолчанию не установлено на некоторое другое значение. Другое значение может иметь тип (например, контейнер), который может быть ложным в логическом контексте!
PEP 8 является важном чтением для любого программиста Python.
Любой из последних двух, так как val
может потенциально иметь тип, который определяет __eq__()
вернуть правду при прохождении None
.
Лучшая ставка с этими типами вопросов состоит в том, чтобы точно увидеть, какой Python делает. То dis
Модуль невероятно информативный:
>>> def f(val):
... if val != None:
... return True
... return False
...
>>> def g(val):
... if not (val is None):
... return True
... return False
...
>>> def h(val):
... if val is not None:
... return True
... return False
...
>>> import dis
>>> dis.dis(f)
2 0 LOAD_FAST 0 (val)
3 LOAD_CONST 0 (None)
6 COMPARE_OP 3 (!=)
9 POP_JUMP_IF_FALSE 16
3 12 LOAD_GLOBAL 1 (True)
15 RETURN_VALUE
4 >> 16 LOAD_GLOBAL 2 (False)
19 RETURN_VALUE
>>> dis.dis(g)
2 0 LOAD_FAST 0 (val)
3 LOAD_CONST 0 (None)
6 COMPARE_OP 9 (is not)
9 POP_JUMP_IF_FALSE 16
3 12 LOAD_GLOBAL 1 (True)
15 RETURN_VALUE
4 >> 16 LOAD_GLOBAL 2 (False)
19 RETURN_VALUE
>>> dis.dis(h)
2 0 LOAD_FAST 0 (val)
3 LOAD_CONST 0 (None)
6 COMPARE_OP 9 (is not)
9 POP_JUMP_IF_FALSE 16
3 12 LOAD_GLOBAL 1 (True)
15 RETURN_VALUE
4 >> 16 LOAD_GLOBAL 2 (False)
19 RETURN_VALUE
Обратите внимание, что последние два случая уменьшаются к той же последовательности операций (Python Reads not (val is None)
и использует то is not
Оператор). Первый использует !=
Оператор при сравнении с ним нет.
Как указано другими ответами, используя !=
При сравнении с ни одной плохой идеей