Итак, у Python есть положительная и отрицательная бесконечность:
float("inf"), float("-inf")
Это похоже на тип функции, который должен иметь некоторые оговорки. Есть ли что-нибудь, о чем я должен знать?
Итак, у Python есть положительная и отрицательная бесконечность:
float("inf"), float("-inf")
Это похоже на тип функции, который должен иметь некоторые оговорки. Есть ли что-нибудь, о чем я должен знать?
Вы все равно можете получить значения not-a-number (NaN) из простой арифметики с участием inf:
>>> 0 * float("inf")
nan
Обратите внимание, что вы обычно не получаете значение inf через обычные арифметические вычисления:
>>> 2.0**2
4.0
>>> _**2
16.0
>>> _**2
256.0
>>> _**2
65536.0
>>> _**2
4294967296.0
>>> _**2
1.8446744073709552e+19
>>> _**2
3.4028236692093846e+38
>>> _**2
1.157920892373162e+77
>>> _**2
1.3407807929942597e+154
>>> _**2
Traceback (most recent call last):
  File "<stdin>", line 1, in ?
OverflowError: (34, 'Numerical result out of range')
Значение inf считается очень особенным значением с необычной семантикой, поэтому лучше знать о OverflowError сразу через исключение, а не иметь значение inf, которое тихо вводится в ваши вычисления.
Реализация Python следует стандарт IEEE-754 довольно хорошо, который вы можете использовать в качестве руководства, но он полагается на базовую систему, на которой он был скомпилирован, поэтому могут возникать различия в платформе . Недавно было применено исправление, которое позволяет "бесконечность" , а также "inf" , но это имеет второстепенное значение.
Следующие разделы одинаково хорошо применимы к любому языку, который правильно выполняет арифметику с плавающей запятой IEEE, это не относится только к Python.
При работе с операторами бесконечности и большей, чем > или менее <, следующие значения:
+inf, больше, чем -inf-inf, меньше +inf+inf не выше и ниже, чем +inf-inf не выше и ниже -infNaN ложно (inf не выше и не ниже NaN)При сравнении для равенства +inf и +inf равны, как и -inf и -inf. Это очень обсуждаемый вопрос и может показаться спорным для вас, но в стандарте IEEE и Python ведет себя так же, как это.
Конечно, +inf не соответствует -inf, и все, включая NaN, неравномерно NaN.
Большинство вычислений с бесконечностью дадут бесконечность, если оба операнда не являются бесконечными, когда операционное деление или по модулю или с умножением на ноль есть некоторые специальные правила, которые следует иметь в виду:
NaN0.0 или -0.0 ².NaN.inf - inf результат undefined: NaN;inf - -inf результат inf;-inf - inf результат -inf;-inf - -inf результат undefined: NaN.inf + inf результат inf;inf + -inf результат undefined: NaN;-inf + inf результат undefined: NaN;-inf + -inf результат -inf.math.pow, pow или ** сложно, так как оно не ведет себя так, как должно. Он генерирует исключение переполнения, когда результат с двумя действительными числами слишком высок, чтобы соответствовать плаванию с двойной точностью (он должен возвращать бесконечность), но когда ввод inf или -inf, он ведет себя корректно и возвращает либо inf или 0.0. Когда второй аргумент NaN, он возвращает NaN, если первый аргумент не равен 1.0. Есть больше проблем, не все описанные в документах. math.exp имеет те же проблемы, что и math.pow. Решение исправить это для переполнения - использовать код, подобный этому:
try:
    res = math.exp(420000)
except OverflowError:
    res = float('inf')
Примечание 1: в качестве дополнительной оговорки, которая, как определено стандартом IEEE, если результат вычисления будет недостаточным или переполнен, результат не будет ошибкой недо- или переполнения, но положительной или отрицательной бесконечностью: 1e308 * 10.0 дает inf.
Примечание 2: поскольку любой расчет с помощью NaN возвращает NaN и любое сравнение с NaN, включая NaN себя false, вы должны использовать math.isnan, чтобы определить, действительно ли число NaN.
Примечание 3: хотя Python поддерживает запись float('-NaN'), знак игнорируется, потому что внутри NaN не существует знака внутри. Если вы разделите -inf / +inf, результат будет NaN, а не -NaN (такой вещи нет).
Примечание 4: будьте осторожны с любым из вышеперечисленных способов, поскольку Python полагается на библиотеку C или Java, для которой он был скомпилирован, а не все базовые системы правильно реализуют все это поведение. Если вы хотите быть уверенным, испытайте бесконечность перед выполнением вычислений.
¹) В последнее время означает, что версия 3.2. 
²) Плавающие точки поддерживают положительный и отрицательный ноль, поэтому: x / float('inf') сохраняет свой знак и -1 / float('inf') дает -0.0, 1 / float(-inf) дает -0.0, 1 / float('inf') дает 0.0 и -1/ float(-inf) дает 0.0, Кроме того, 0.0 == -0.0 - true, вам нужно вручную проверить знак, если вы не хотите, чтобы оно было истинным.
Итак, C99.
Представление с плавающей запятой IEEE 754, используемое всеми современными процессорами, имеет несколько специальных битовых шаблонов, зарезервированных для положительной бесконечности (знак = 0, exp = ~ 0, frac = 0), отрицательная бесконечность (знак = 1, exp = ~ 0, frac = 0) и много NaN (не число: exp = ~ 0, frac ≠ 0).
Все, о чем вам нужно беспокоиться: некоторые арифметические действия могут вызывать исключения/ловушки с плавающей запятой, но они не ограничиваются только этими "интересными" константами.
Я нашел оговорку, о которой никто до сих пор не упомянул. Я не знаю, будет ли это часто встречаться в практических ситуациях, но здесь это ради полноты.
Обычно вычисление числа по модулю бесконечности возвращает себя как число с плавающей запятой, но дробь по модулю бесконечности возвращает nan (не число). Вот пример:
>>> from fractions import Fraction
>>> from math import inf
>>> 3 % inf
3.0
>>> 3.5 % inf
3.5
>>> Fraction('1/3') % inf
nan
Я подал проблему на трекер ошибок Python. Это можно увидеть на https://bugs.python.org/issue32968.
Обновление: это будет исправлено в Python 3.8.
ОЧЕНЬ ПЛОХАЯ ПЕРЕДАЧА: Деление на ноль
во фракции 1/x, до x = 1e-323 это inf, но когда x = 1e-324 или мало, он выбрасывает ZeroDivisionError
>>> 1/1e-323
inf
>>> 1/1e-324
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ZeroDivisionError: float division by zero
так что будь осторожен!