Re: Окажите помощь



Posted by Аркадий Водяник on February 03, 2000 at 00:24:38:

In Reply to: Окажите помощь posted by Демехина Яна on February 02, 2000 at 01:55:26:

Уважаемая Яна!

Да, такая eсть проблема: "проскакивание" мимо явно подходящих
фактов-кандидатов на сопоставление, если в составе образца
для сопоставления есть некоторые числа с плавающей точкой.

В моем сообщении 205 я показал, как устроено
сопоставление образца с фактом. Как увидите там, это не совсем
одинаково для однопользовательских версий и ФБП:Сервера.

В ленте фактов числа хранятся в нормализованной форме записи,
и при чтении такого числа из текста и преобразовании в собственно
число, используется одна из библиотек фирмы Watcom. А при чтении
числа из операции (a там оно и не нормализованное) используется другой
алгоритм.И в том и другом числе случае получаются числа double
(8-байт), которые хранят мантиссу представимую в десятичном представлении
как 13-14 знаков (никaкого упомянутого Вами 17-го знака там быть
не может, это все ложные знаки, показываемые программами печати по
заданному формату). Не все биты в этих восьмибайтовых представлениях
совпадают, так что неудивительно, что после описанного в 205
"загрубления" в тип float (4 байта) для некоторых чисел получаются
расхождения.

Почему же числа равны при сравнении оператором '='?
Дело в том, что оператор '=' использует другой метод загрубления:
x = y, если abs(x-y) < delta, где delta=0.00001. Тоже ничего хорошего
для некоторых алгоритмов.

Что же делать? Как уже говорили Анатолий и Александр - лучше
отдавать предпочтение хранению в полях факта строк, а не чисел.
Тем более, что при этом зачастую получается экономия - для числового поля
0.09 требовалось 8 байт (double) в факте, а для строки '0.09' - 5 байт
(это с учетом байта длины строки).

Так что извините меня за источник ненадежности и дополнительной работы,
но проблема сравнения действительных чисел все-равно никуда не
исчезнет, и всегда придется иметь дело с какими-то delta.



Пpишедшие ответы: