igorbor: (Default)
[personal profile] igorbor
Однажды приятель, работающий в Хеврат Хашмаль, прислал мне на работу письмо с заголовком: "Смотри, как в нашей конторе проверяют две переменные на равенство" и кусочком кода на несколько строчек:

if( a > b)
{
/* Do nothing */
}
else if( a < b)
{
/* Do nothing */
}
else
{
блаблабла - тут был написан какой-то реальный код.
}


Я посмеялся в усы и тут же переслал это письмо всем на фирме - только на всякий случай, чтобы не подставлять мужика (кто знает, какие у них там порядки в Хеврат Хашмале), вырезал все его данные и написал только, что вот, мол, этот код - не просто шутка, а кусок живой программы. Пусть, думаю, народ повеселится.

Через три минуты мне пришло ДВА ответа примерно одинакового содержания: "It's not me, it was there before"

Date: 2003-09-04 02:54 pm (UTC)
From: [identity profile] cmm.livejournal.com
ежели иметь дело с плавающей точкой, то так писать вполне даже и разумно.

(дисклямер: я давно не имел дел с плавающей точкой, посему могу и гнать.)

Date: 2003-09-04 03:33 pm (UTC)
From: [identity profile] trurle.livejournal.com
Никак нет. Прелесть плавающей точки в том что она представляет числа приближенно. Поэтому проверка
if (x==sqrt(x*x))
может сработать совсем не так как того ожидает наивный программист.
Но уж если представление отличается от точного, то оно либо меньше, либо больше.
правильно писать
if (fabs(x-sqrt(x*x))
[Error: Irreparable invalid markup ('<eps)>') in entry. Owner must fix manually. Raw contents below.]

Никак нет. Прелесть плавающей точки в том что она представляет числа приближенно. Поэтому проверка
if (x==sqrt(x*x))
может сработать совсем не так как того ожидает наивный программист.
Но уж если представление отличается от точного, то оно либо меньше, либо больше.
правильно писать
if (fabs(x-sqrt(x*x))<EPS)
где EPS - допустимая ошибка.
А код из примера <lj site="livejournal.com" user="igorbor"> решительно ничему не помогает

Date: 2003-09-04 03:52 pm (UTC)
From: [identity profile] cmm.livejournal.com
дык ну?
проверять на равенство "в лоб" в таком случае неразумно, натурально.
но заключать "равно" исходя из того, что "и не меньше, и не больше", по-моему, нормально.
(хотя рисовать пустые if'ы глупо всё равно, конечно же)

Date: 2003-09-04 03:58 pm (UTC)
From: [identity profile] trurle.livejournal.com
но заключать "равно" исходя из того, что "и не меньше, и не больше", по-моему, нормально.
Нет. Положим, sqrt(16) будет не 4, а 3.99999999. Тогда сработает ветка "меньше" - и чего мы добились?

Date: 2003-09-04 04:10 pm (UTC)
From: [identity profile] cmm.livejournal.com
> и чего мы добились?

резонного вывода "чёрт подери, а ведь вычисления с плавающей точкой могут быть неточны!".
я собственно всё к чему?  к тому что логика типа "if a > b stuff else if a < b stuff else stuff" не обязательно избыточна, а не к тому что последняя ветка в ней так уж информативна. :)

(прошу прощения за пустой коммент, ЖЖ глючит)

Date: 2003-09-04 06:05 pm (UTC)
From: [identity profile] igorbor.livejournal.com
Все это верно. Но к конкретному примеру отношения не имеет. Обычные целые числа.

Date: 2003-09-05 12:45 am (UTC)
From: [identity profile] trurle.livejournal.com
Я [livejournal.com profile] cmm отвечаю.

Date: 2003-09-05 08:10 am (UTC)
From: [identity profile] cema.livejournal.com


Конечно, и всё же сравнение с нулём особый случай.

Date: 2003-09-05 08:21 am (UTC)
From: [identity profile] trurle.livejournal.com
Не очень понял, честно говоря.
(asin(1)-M_PI/2) может запросто оказаться отличным от 0.

Date: 2003-09-06 10:23 am (UTC)
From: [identity profile] arbat.livejournal.com

Вообще-то мне казажется, что как раз это должно сработать, если плавающие числа удовлетворяют IEEE. Стандарт требует, чтобы определенные операции давали именно как раз - четкое соответствие между аргументами и результатами. Не помню - какие именно операции и функции включены.

Page generated Dec. 27th, 2025 08:23 pm
Powered by Dreamwidth Studios