Плавающая запятая и разные процессоры
Модератор: Модераторы
Плавающая запятая и разные процессоры
Здравствуйте!
Я столкнулся с проблемой, что на разных машинах по-разному вычисляются выражения с плавающей запятой. В связи с этим у меня возник вопрос, возможно ли сделать так, чтобы на разных процессорах получался одинаковый результат? Пробовал искать что-нибудь по теме, не нашёл решения для паскаля. Для gcc, видимо, ключик подойдёт -mieee-conformant.
Подскажите, пожалуйста, существует ли решение моей проблемы? Решат ли проблему вычисления с эмуляцией?
Я столкнулся с проблемой, что на разных машинах по-разному вычисляются выражения с плавающей запятой. В связи с этим у меня возник вопрос, возможно ли сделать так, чтобы на разных процессорах получался одинаковый результат? Пробовал искать что-нибудь по теме, не нашёл решения для паскаля. Для gcc, видимо, ключик подойдёт -mieee-conformant.
Подскажите, пожалуйста, существует ли решение моей проблемы? Решат ли проблему вычисления с эмуляцией?
- Slavikk
- постоялец
- Сообщения: 208
- Зарегистрирован: 15.01.2007 21:34:52
- Откуда: Из лесов...
- Контактная информация:
На разных машинах это AMD - Intel, или Intel Pentium3 - Intel Pentium4?
Если это AMD - Intel, то читал что из-за разной архитектуры одни процессоры лучше считают точные цифры, другие с плавающей запятой. И у кого то из них проблемы были они один тип расчетов эмулировали через другой - и появлялась погрешность. Вроде так, точно непомню, врать не буду, могу и ошибаться.
Толь ответ тебе даст их официальные сайт с туториалами на английском (хорошо хоть не на албанском) и кодами скорее всего на С++ (но могут быть и на Асемблере).
Если это AMD - Intel, то читал что из-за разной архитектуры одни процессоры лучше считают точные цифры, другие с плавающей запятой. И у кого то из них проблемы были они один тип расчетов эмулировали через другой - и появлялась погрешность. Вроде так, точно непомню, врать не буду, могу и ошибаться.
Толь ответ тебе даст их официальные сайт с туториалами на английском (хорошо хоть не на албанском) и кодами скорее всего на С++ (но могут быть и на Асемблере).
- shade
- энтузиаст
- Сообщения: 879
- Зарегистрирован: 21.02.2006 19:15:48
- Откуда: http://shamangrad.net/
- Контактная информация:
Slavikk писал(а):На разных машинах это AMD - Intel, или Intel Pentium3 - Intel Pentium4?
На разных машинах - это от пентиума 1 до Core 2 Duo, от K6 до AMD64, также PowerPC и возможно другие процессоры.
Slavikk писал(а):из-за разной архитектуры одни процессоры лучше считают точные цифры, другие с плавающей запятой. И у кого то из них проблемы были они один тип расчетов эмулировали через другой - и появлялась погрешность.
"Точные" - это целые? Погрешность при рассчётах в целых числах? Ужос %)
shade писал(а):Результаты нужно округлять, тогда проблемы могут быть только из-за недостаточной разрядности или численной неустойчивости алгоритма.
Округлять? Каким образом? Скажем, идёт рассчёт кривой Безье. Точки рисуются в битмапы, картинка получается разной. Чуть-чуть, буквально пара пикселов. При том что используется тип Extended... Я в растерянности.
Юра писал(а):На любом х86 процессоре результаты будут одинаковыми.
Почему-то получаются разные. Конкретно - пентиум4, 32-битный код и амд64, 64битный код. Пробовал типы Double и Extended, разница есть. Особенно обидно когда разница возникает при проверке условий больше-меньше, при этом работает разный код и конечные результаты получаются ещё более разными.
- shade
- энтузиаст
- Сообщения: 879
- Зарегистрирован: 21.02.2006 19:15:48
- Откуда: http://shamangrad.net/
- Контактная информация:
unC0Rr писал(а):Особенно обидно когда разница возникает при проверке условий больше-меньше, при этом работает разный код и результаты получаются ещё более разными.
Условия нужно проверять с учетом погрешности:
Проверка на ноль
Код: Выделить всё
if abs(a) < e then ... else ...А аналогично для сравнения больше:
Код: Выделить всё
if a + e > b then ...
if a - b > e then ...
if a - b > -e then...меньше:
Код: Выделить всё
if a - e < b then ...
if a - b < e then ...
if a - b < -e then ...или что-то в этом духе, точные формы не припомню.
unC0Rr писал(а):Чуть-чуть, буквально пара пикселов.
Один-в-один врядли добьешься, но может удасться улучшить результат до погрешности в пол пикселя. Вопрос в том как вычисляешь, как преобразуешь действительное к целому.
Попробуй для расчетов и использовать другой масштаб (смысл в том чтобы увеличить точность в расчетах с плавающей точкой):
например (x, y) - целочисленные координаты, а (u, v) - соответствующие действительные координаты.
Преобразование u := 2 * x; v := 2 * y; обратное: x := Round(u / 2), y := Round(v / 2)
или x := Round(u) div 2; y := Round(v) div 2;
По экспериментируй с другим множителем...
shade писал(а):Условия нужно проверять с учетом погрешности:
Проверка на нольгде e - допустимая погрешность.Код: Выделить всё
if abs(a) < e then ... else ...
А аналогично для сравнения больше:Код: Выделить всё
if a + e > b then ...
if a - b > e then ...
if a - b > -e then...
меньше:Код: Выделить всё
if a - e < b then ...
if a - b < e then ...
if a - b < -e then ...
или что-то в этом духе, точные формы не припомню.
Да, начитался я таких советов
Код: Выделить всё
if (tx - Gear1^.X) * (ty - Gear2^.Y) > (tx - Gear2^.X) * (ty - Gear1^.Y) then ...
Куда тут погрешности вставить и чем они могут помочь? имхо, ничем
- shade
- энтузиаст
- Сообщения: 879
- Зарегистрирован: 21.02.2006 19:15:48
- Откуда: http://shamangrad.net/
- Контактная информация:
- shade
- энтузиаст
- Сообщения: 879
- Зарегистрирован: 21.02.2006 19:15:48
- Откуда: http://shamangrad.net/
- Контактная информация:
Код: Выделить всё
if (tx - Gear1^.X) * (ty - Gear2^.Y) - (tx - Gear2^.X) * (ty - Gear1^.Y) > -e then ... Зачем одинаковые результаты при вычислениях?
Дело в том, что компьютеры взаимодействуют по сети, и при разных результатах вычислений взаимодействие невозможно. Выполнять вычисления только на одной машине невозможно, трафик при этом может составлять несколько мегабайт в секунду, а использовать приложение предполагается посредством интернета.
- shade
- энтузиаст
- Сообщения: 879
- Зарегистрирован: 21.02.2006 19:15:48
- Откуда: http://shamangrad.net/
- Контактная информация:
Извени, то было >=
а просто >
а просто >
shade писал(а):Код: Выделить всё
if (tx - Gear1^.X) * (ty - Gear2^.Y) - (tx - Gear2^.X) * (ty - Gear1^.Y) > +e then ...
shade писал(а):Код: Выделить всё
if (tx - Gear1^.X) * (ty - Gear2^.Y) - (tx - Gear2^.X) * (ty - Gear1^.Y) > -e then ...
Т.е.
Код: Выделить всё
if (tx - Gear1^.X) * (ty - Gear2^.Y) > (tx - Gear2^.X) * (ty - Gear1^.Y) + e then ... ???
