Я ожидал, что результат должен быть True, поскольку я думал, что неизменяемые числовые объекты (или их кортежи) имеют только один экземпляр.
Это ожидание сомнительно - таких нетвещь гарантируется языком Python.
is
- довольно сложный оператор, потому что вам действительно нужно знать, когда его целесообразно использовать.
Например:
>>> 5 / 2 is 2.5
>>> (1, 2, 3) is (1, 2, 3)
Это нецелесообразное использование is
в общем случае.Они могут быть подходящими, если вы хотите проверить, что делает оптимизация строк / функций (интернирование) Python, но я думаю, что это не тот вариант использования.
is
следует использовать только, если вы хотитесравнивать с константами (которые гарантированно имеют только один экземпляр)! Гарантированные встроенные константы :
None
NotImplemented
Ellipsis
(также известный как * 1031)*) True
False
__debug__
Или ваши собственные постоянные экземпляры:
_sentinel = object()
def func(a=_sentinel):
return a is _sentinel
Или когда вы явно назначаете переменные для нового имени:
a = b
a is b # <- that's expected to be True
Кто-нибудь знает, какие изменения были внесены, что объясняет это новое поведение?
Вероятно, оптимизатор глазков теперь оптимизирует больше случаев (кортежи и математические выражения).Например, «сворачивание констант уровня AST» (https://bugs.python.org/issue29469) был добавлен в CPython 3.7 (я специально написал здесь CPython, потому что это ничего не было добавлено в спецификацию языка Python 3.7).