Является ли инверсия std::numeric_limits::infinity() нулевой?

Есть ли что-нибудь в стандарте C++ (или стандарте IEEE 754 с плавающей запятой), что гарантирует, что 1./std::numeric_limits<double>::infinity() равно нулю (или, по крайней мере, небольшому числу)?


person davidhigh    schedule 25.08.2018    source источник
comment
Посмотрите floating-point-gui.de   -  person Basile Starynkevitch    schedule 25.08.2018
comment
Очень похоже.   -  person user202729    schedule 25.08.2018


Ответы (4)


Да, согласно справочному руководству по библиотеке GNU C (при условии IEEE 754):

Бесконечности распространяются через вычисления, как и следовало ожидать: например, 2 + = , 4/ = 0

https://www.gnu.org/software/libc/manual/html_node/Infinity-and-NaN.html

Вы можете проверить, использует ли ваш компилятор C++ IEEE 754:

Как проверить, является ли C++ компилятор использует стандарт IEEE 754 с плавающей запятой

person Gonen I    schedule 25.08.2018

Любое конечное число, деленное на бесконечность, дает нуль в соответствии с IEEE 754 (и, следовательно, то же самое в большинстве типичных реализаций C++).

Если знак числителя и знаменателя различаются, результатом будет отрицательный нуль, который равен нулю.

person John Zwinck    schedule 25.08.2018
comment
Хм, нет, не совсем так: если конечное число отрицательно, оно возвращает -0, что не то же самое, что 0 (хотя при сравнении оно равно). - person Federico Poloni; 25.08.2018
comment
Да, правильная формулировка будет означать a ноль :) - person Ruslan; 25.08.2018
comment
@FedericoPoloni: +0 и -0 на уровне 2 спецификации IEEE 754 (данные с плавающей запятой) представляют ноль на уровне 1 (расширенные действительные числа). - person Eric Postpischil; 25.08.2018

IEEE 754-2008 6.1 говорит:

Поведение бесконечности в арифметике с плавающей запятой выводится из предельных случаев вещественной арифметики с операндами произвольно большой величины, когда такой предел существует. Бесконечности следует интерпретировать в аффинном смысле, то есть: −∞ ‹ {каждое конечное число} ‹ +∞.

Операции с бесконечными операндами обычно точны и поэтому не сигнализируют об исключениях…

Поскольку предел 1/x при неограниченном увеличении x равен нулю, следствием этого пункта является то, что 1/∞ равно нулю.

Пункт 6.3 говорит нам, что знак результата равен +:

Когда ни входные данные, ни результат не являются NaN, знак произведения или частного является исключающим ИЛИ знаков операндов;…

person Eric Postpischil    schedule 25.08.2018

if(std::numeric_limits<double>::is_iec559) yes(); else no();

(см. 18.3.2.4)

IEC 559, который идентичен IEEE 754, гарантирует, что это так. Однако C++ никоим образом не гарантирует, что IEC 559 действует (хотя в 99,99% случаев именно так и происходит, вам все равно нужно проверить, чтобы быть уверенным).

person Damon    schedule 25.08.2018
comment
Поскольку вряд ли кто-то будет утруждать себя реализацией и тестированием платформ, отличных от IEEE 754, можно было бы также static_assert(std::numeric_limits<double>::is_iec559). - person John Zwinck; 26.08.2018
comment
@JohnZwinck: Это действительно хороший момент. Если ваш код опирается на данные IEEE 754, он не будет работать, если они отсутствуют. Так что static_assert — очень правильный вариант (возможно, даже лучший). - person Damon; 26.08.2018