Значения с плавающей запятой неточны, поэтому нам редко следует использовать строгое числовое равенство при сравнениях. Например, в Java это печатает false
(как показано на ideone.com):
System.out.println(.1 + .2 == .3);
// false
Обычно правильный способ сравнить результаты вычислений с плавающей запятой - увидеть, меньше ли абсолютная разница с некоторым ожидаемым значением, чем некоторое допустимое эпсилон.
System.out.println(Math.abs(.1 + .2 - .3) < .00000000000001);
// true
Вопрос в том, могут ли некоторые операции давать точный результат. Мы знаем, что для любого не конечного значения с плавающей запятой x
(т. Е. NaN
или бесконечности) x - x
равно < em> ВСЕГДА NaN
.
Но если x
конечно, гарантировано ли что-нибудь из этого?
x * -1 == -x
x - x == 0
(В частности, меня больше всего интересует поведение Java, но дискуссии о других языках также приветствуются.)
Как бы то ни было, я думаю (и здесь я могу ошибаться) ответ - ДА! Я думаю, что все сводится к тому, для какого-либо конечного IEEE-754 значение с плавающей запятой, его аддитивная инверсия всегда точно вычислима. Так как, например, float
и double
имеет один выделенный бит только для знака, похоже, это так , поскольку для нахождения аддитивной инверсии требуется только перевернуть знаковый бит (т. е. значащий оставить нетронутым).