ieee float что это

IEEE-представление с плавающей точкой

Значения хранятся в следующем виде:

Значение Хранение
одиночная точность разряд знака, 8 разрядов показателя степени, 23 разряда значащей части
двойная точность разряд знака, 11 разрядов показателя степени, 52 разряда значащей части

В форматах с одиночной и двойной точностью в дробной части предполагается первый символ 1. Дробная часть называется значащей частью или мантиссой. Это начальное значение 1 не сохраняется в памяти, так что по сути значащая часть имеет длину 24 или 53 бита, из которых хранится на один бит меньше. В формате расширенной двойной точности этот разряд сохраняется в памяти.

Величина показателя степени смещена наполовину относительно возможного значения. Это значит, что для получения фактического значения экспоненты необходимо вычесть это смещение из хранящегося в памяти значения. Если сохраненное в памяти значение экспоненты меньше смещения, значит экспонента отрицательная.

Смещение показателя степени определяется следующим образом:

Показатель степени Величина смещения
8 разрядов (одиночная точность) 127
11 разрядов (двойная точность) 1023

Эти экспоненты определяют показатели степени для двойки, а не для десятки. Таким образом, для 8-разрядного формата фактические показатели степени в диапазоне от –127 до 127 хранятся в памяти соответственно в виде значений в диапазоне от 0 до 254. Значение 2 127 примерно равно 10 38 и определяет фактический предел для чисел с одиночной точностью.

Значащая часть хранится в виде двоичной части в форме 1.XXX. Эта часть имеет значение больше 1 и меньше 2. Вещественные числа всегда хранятся в нормализованном представлении. В частности, значение значащей части всегда смещается влево, чтобы ее старший бит имел значение 1. Так как этот разряд всегда равен 1, для форматов одиночной и двойной точности его значение принимается по умолчанию и не хранится в памяти. Двоичная (не десятичная) точка располагается непосредственно справа от начальной 1.

Формат представления с плавающей запятой выглядит следующим образом:

Формат байт 1 байт 2 байт 3 байт 4 . байт n
одиночная точность SXXXXXXX XMMMMMMM MMMMMMMM MMMMMMMM
двойная точность SXXXXXXX XXXXMMMM MMMMMMMM MMMMMMMM . MMMMMMMM

S представляет разряд знака, X — это разряды смещенного показателя степени, а M — это значащие разряды. В форматах одиночной и двойной точности значение самого левого бита предполагается.

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

Специальные значения

Форматы с плавающей запятой предусматривают некоторые значения, которые обрабатываются особым образом.

Значение нуля невозможно представить в нормализованном виде, который используется для форматов одиночной и двойной точности. Таким образом, для определения значения 0 используется специальный шаблон, состоящий из нулей. При необходимости с помощью разряда знака можно представить значение –0, однако оно всегда будет сопоставляться как равное 0.

Бесконечность

Значения +∞ и −∞ представляются с экспонентой из одних единиц и мантиссой из одних нулей. Разряд знака определяет знак бесконечности.

Субнормальные числа

Числа, которые находятся ближе к нулю, чем наименьшее число в нормализованном преставлении, могут быть представлены. Такие числа называются субнормальными или денормализованными. Если показатель степени представлен одними нулевыми значениями, а значащая часть отлична от нуля, старший бит значащей части принимается равным нулю, а не единице. Точность субнормальных чисел снижается по мере увеличения количества начальных нулей в значащей части.

NaN (не число)

В формате IEEE с плавающей запятой могут быть представлены значения, не являющиеся действительными числами, например 0/0. Значения такого вида называются NaN (не число). Значение NaN представляется состоящим из единиц показателем степени и отличной от нуля значащей частью. Существует два вида значений NaN: несигнальные (QNaN) и сигнальные (SNaN). Для несигнальных значений NaN старший разряд значащей части равен единице, и эти значения распространяются через выражения. Они представляют неопределенные значения, например результат деления на бесконечность или умножения бесконечности на нуль. Для сигнальных значений NaN старший разряд значащей части равен нулю. Эти значения используются для недопустимых операций, указывая на аппаратное исключение, связанное с обработкой чисел с плавающей запятой.

Примеры

Ниже приводятся примеры чисел в формате одиночной точности:

Для значения 2 знаковый бит имеет значение 0. Сохраняется экспонента 128, то есть двоичное значение 1000 0000, вычисляемое как 127 плюс 1. Сохраненный двоичный значащим имеет значение (1). 000 0000 0000 0000 0000 0000, которая имеет неявные начальные значения 1 и binary, поэтому фактический значащим является одним.

Значение Формула Двоичное представление Шестнадцатеричный
2 1 * 2 1 0100 0000 0000 0000 0000 0000 0000 0000 0x40000000

Значение –2. То же, что и + 2, однако в этом случае задан разряд знака. Таким же образом задаются отрицательные числа во всех форматах IEEE с плавающей запятой.

Значение Формула Двоичное представление Шестнадцатеричный
-2 –1 * 2 1 1100 0000 0000 0000 0000 0000 0000 0000 0xC0000000

Значение 4. Та же значащая часть, показатель степени увеличивается на единицу (смещенное значение 129 или 100 0000 1 в двоичном формате).

Значение Формула Двоичное представление Шестнадцатеричный
4 1 * 2 2 0100 0000 1000 0000 0000 0000 0000 0000 0x40800000

Значение 6. Тот же показатель степени; значащая часть увеличивается наполовину. Это (1.) 100 0000. 0000 0000, что, поскольку это двоичная дробь, имеет значение 1 1/2, так как значения дробных разрядов равны 1/2, 1/4, 1/8 и т. д.

Значение Формула Двоичное представление Шестнадцатеричный
6 1.5 * 2 2 0100 0000 1100 0000 0000 0000 0000 0000 0x40C00000

Значение 1. Та же значащая часть, что и для остальных степеней двух; смещенный показатель степени на единицу меньше, чем у двух при 127, то есть 011 1111 1 в двоичном формате.

Значение Формула Двоичное представление Шестнадцатеричный
1 1 * 2 0 0011 1111 1000 0000 0000 0000 0000 0000 0x3F800000

Значение 0,75. Смещенный показатель степени равен 126, 011 1111 0 в двоичном формате, а значащим имеет значение (1). 100 0000. 0000 0000, то есть 1 1/2.

Значение 2,5. Так же, как и два, однако в значащей части задан разряд, который представляет 1/4.

Значение Формула Двоичное представление Шестнадцатеричный
2.5 1.25 * 2 1 0100 0000 0010 0000 0000 0000 0000 0000 0x40200000

1/10 — это повторяющаяся часть в двоичном формате. Значащая часть здесь немного меньше 1,6, а экспонента с учетом смещения указывает, что 1,6 нужно разделить на 16. (Это 011 1101 1 в двоичном формате, то есть 123 в десятичном формате.) Фактический показатель степени 123 – 127 = –4. Это значит, что выполняется умножение на 2 –4 = 1/16. Хранимая в памяти значащая часть округляется до последнего разряда, чтобы представить выходящие за пределы числа с максимально возможной точностью. (Величины 1/10 и 1/100 нельзя точно представить в двоичном формате по той же причине, по которой 1/3 нельзя представить в десятичном.)

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

Источник

Что нужно знать про арифметику с плавающей запятой

В далекие времена, для IT-индустрии это 70-е годы прошлого века, ученые-математики (так раньше назывались программисты) сражались как Дон-Кихоты в неравном бою с компьютерами, которые тогда были размером с маленькие ветряные мельницы. Задачи ставились серьезные: поиск вражеских подлодок в океане по снимкам с орбиты, расчет баллистики ракет дальнего действия, и прочее. Для их решения компьютер должен оперировать действительными числами, которых, как известно, континуум, тогда как память конечна. Поэтому приходится отображать этот континуум на конечное множество нулей и единиц. В поисках компромисса между скоростью, размером и точностью представления ученые предложили числа с плавающей запятой (или плавающей точкой, если по-буржуйски).

Арифметика с плавающей запятой почему-то считается экзотической областью компьютерных наук, учитывая, что соответствующие типы данных присутствуют в каждом языке программирования. Я сам, если честно, никогда не придавал особого значения компьютерной арифметике, пока решая одну и ту же задачу на CPU и GPU получил разный результат. Оказалось, что в потайных углах этой области скрываются очень любопытные и странные явления: некоммутативность и неассоциативность арифметических операций, ноль со знаком, разность неравных чисел дает ноль, и прочее. Корни этого айсберга уходят глубоко в математику, а я под катом постараюсь обрисовать лишь то, что лежит на поверхности.

1. Основы

Множество целых чисел бесконечно, но мы всегда можем подобрать такое число бит, чтобы представить любое целое число, возникающее при решении конкретной задачи. Множество действительных чисел не только бесконечно, но еще и непрерывно, поэтому, сколько бы мы не взяли бит, мы неизбежно столкнемся с числами, которые не имеют точного представления. Числа с плавающей запятой — один из возможных способов предсталения действительных чисел, который является компромиссом между точностью и диапазоном принимаемых значений.

Число с плавающей запятой состоит из набора отдельных разрядов, условно разделенных на знак, экспоненту порядок и мантиссу. Порядок и мантисса — целые числа, которые вместе со знаком дают представление числа с плавающей запятой в следующем виде:

Математически это записывается так:

Основание определяет систему счисления разрядов. Математически доказано, что числа с плавающей запятой с базой B=2 (двоичное представление) наиболее устойчивы к ошибкам округления, поэтому на практике встречаются только базы 2 и, реже, 10. Для дальнейшего изложения будем всегда полагать B=2, и формула числа с плавающей запятой будет иметь вид:

Что такое мантисса и порядок? Мантисса – это целое число фиксированной длины, которое представляет старшие разряды действительного числа. Допустим наша мантисса состоит из трех бит (|M|=3). Возьмем, например, число «5», которое в двоичной системе будет равно 1012. Старший бит соответствует 2 2 =4, средний (который у нас равен нулю) 2 1 =2, а младший 2 0 =1. Порядок – это степень базы (двойки) старшего разряда. В нашем случае E=2. Такие числа удобно записывать в так называемом «научном» стандартном виде, например «1.01e+2». Сразу видно, что мантисса состоит из трех знаков, а порядок равен двум.

Допустим мы хотим получить дробное число, используя те же 3 бита мантиссы. Мы можем это сделать, если возьмем, скажем, E=1. Тогда наше число будет равно

2 = 10 (в двоичной системе) = 1.000e+1 = 0.100e+2 = 0.010e+3. (E=1, E=2, E=3 соответственно)

Обратите внимание, что одно и то же число имеет несколько представлений. Это не удобно для оборудования, т.к. нужно учитывать множественность представлния при сравнении чисел и при выполнении над ними арифметических операций. Кроме того, это не экономично, поскольку число представлений — конечное, а повторения уменьшают множество чисел, которые вообще могут быть представлены. Поэтому уже в самых первых машинах начали использовать трюк, делая первый бит мантиссы всегда положительным. Такое предаставление назвали нормализованным.

Это экономит один бит, так как неявную единицу не нужно хранить в памяти, и обеспечивает уникальность представления числа. В нашем примере «2» имеет единственное нормализованное представление («1.000e+1»), а мантисса хранится в памяти как «000», т.к. старшая единица подразумевается неявно. Но в нормализованном представлении чисел возникает новая проблема — в такой форме невозможно представить ноль.

Строго говоря, нормализованное число имеет следующий вид:

Качество решения задач во многом зависит от выбора представления чисел с плавающей запятой. Мы плавно подошли к проблеме стандартизации такого представления.

2. Немного истории

В 60-е и 70-е годы не было единого стандарта представления чисел с плавающей запятой, способов округления, арифметических операций. В результате программы были крайне не портабельны. Но еще большей проблемой было то, что у разных компьютеров были свои «странности» и их нужно было знать и учитывать в программе. Например, разница двух не равных чисел возвращала ноль. В результате выражения «X=Y» и «X-Y=0» вступали в противоречие. Умельцы обходили эту проблему очень хитрыми трюками, например, делали присваивание «X=(X-X)+X» перед операциями умножения и деления, чтобы избежать проблем.

Инициатива создать единый стандарт для представления чисел с плавающей запятой подозрительно совпала с попытками в 1976 году компанией Intel разработать «лучшую» арифметику для новых сопроцессоров к 8086 и i432. За разработку взялись ученые киты в этой области, проф. Джон Палмер и Уильям Кэхэн. Последний в своем интервью высказал мнение, что серьезность, с которой Intel разрабатывала свою арифметику, заставила другие компании объединиться и начать процесс стандартизации.

Все были настроены серьезно, ведь очень выгодно продвинуть свою архитектуру и сделать ее стандартной. Свои предложения представили компании DEC, National Superconductor, Zilog, Motorola. Производители мейнфреймов Cray и IBM наблюдали со стороны. Компания Intel, разумеется, тоже представила свою новую арифметику. Авторами предложенной спецификации стали Уильям Кэхэн, Джероми Кунен и Гарольд Стоун и их предложение сразу прозвали «K-C-S».

Практически сразу же были отброшены все предложения, кроме двух: VAX от DEC и «K-C-S» от Intel. Спецификация VAX была значительно проще, уже была реализована в компьютерах PDP-11, и было понятно, как на ней получить максимальную производительность. С другой стороны в «K-C-S» содержалось много полезной функциональности, такой как «специальные» и «денормализованные» числа (подробности ниже).

В «K-C-S» все арифметические алгоритмы заданы строго и требуется, чтобы в реализации результат с ними совпадал. Это позволяет выводить строгие выкладки в рамках этой спецификации. Если раньше математик решал задачу численными методами и доказывал свойства решения, не было никакой гарантии, что эти свойства сохранятся в программе. Строгость арифметики «K-C-S» сделала возможным доказательство теорем, опираясь на арифметику с плавающей запятой.

Компания DEC сделала все, чтобы ее спецификацию сделали стандартом. Она даже заручилась поддержкой некоторых авторитетных ученых в том, что арифметика «K-C-S» в принципе не может достигнуть такой же производительности, как у DEC. Ирония в том, что Intel знала, как сделать свою спецификацию такой же производительной, но эти хитрости были коммерческой тайной. Если бы Intel не уступила и не открыла часть секретов, она бы не смогла сдержать натиск DEC.

Подробнее о баталиях при стандартизации смотрите в интервью профессора Кэхэна, а мы рассмотрим, как выглядит представление чисел с плавающей запятой сейчас.

3. Представление чисел с плавающей запятой сегодня

Разработчики «K-C-S» победили и теперь их детище воплотилось в стандарт IEEE754. Числа с плавающей запятой в нем представлены в виде знака (s), мантиссы (M) и порядка (E) следующим образом:

Замечание. В новом стандарте IEE754-2008 кроме чисел с основанием 2 присутствуют числа с основанием 10, так называемые десятичные (decimal) числа с плавающей запятой.

Чтобы не загромождать читателя чрезмерной информацией, которую можно найти в Википедии, рассмотрим только один тип данных, с одинарной точностью (float). Числа с половинной, двойной и расширенной точностью обладают теми же особенностями, но имеют другой диапазон порядка и мантиссы. В числах одинарной точности (float/single) порядок состоит из 8 бит, а мантисса – из 23. Эффективный порядок определяется как E-127. Например, число 0,15625 будет записано в памяти как


Рисунок взят из Википедии

3.1 Специальные числа: ноль, бесконечность и неопределенность

Неопределенность или NaN (от not a number) – это представление, придуманное для того, чтобы арифметическая операция могла всегда вернуть какое-то не бессмысленное значение. В IEEE754 NaN представлен как число, в котором E=Emax+1, а мантисса не нулевая. Любая операция с NaN возвращает NaN. При желании в мантиссу можно записывать информацию, которую программа сможет интерпретировать. Стандартом это не оговорено и мантисса чаще всего игнорируется.

Вернемся к примеру. Наш Emin=-1. Введем новое значение порядка, E=-2, при котором числа являются денормализованными. В результате получаем новое представление чисел:

Интервал от 0 до 0,5 заполняют денормализованные числа, что дает возможность не проваливаться в 0 рассмотренных выше примерах (0,5-0,25 и 1,5-1,25). Это сделало представление более устойчиво к ошибкам округления для чисел, близких к нулю.

Но роскошь использования денормализованного представления чисел в процессоре не дается бесплатно. Из-за того, что такие числа нужно обрабатывать по-другому во всех арифметических операциях, трудно сделать работу в такой арифметике эффективной. Это накладывает дополнительные сложности при реализации АЛУ в процессоре. И хоть денормализованные числа очень полезны, они не являются панацеей и за округлением до нуля все равно нужно следить. Поэтому эта функциональность стала камнем преткновения при разработке стандарта и встретила самое сильное сопротивление.

3.4 Очередность чисел в IEEE754

Одна из удивительных особенностей представления чисел в формате IEEE754 состоит в том, что порядок и мантисса расположены друг за другом таким образом, что вместе образуют последовательность целых чисел для которых выполняется:

4.2 Неассоциативность арифметических операций

В арифметике с плавающей запятой правило (a*b)*c = a*(b*c) не выполняется для любых арифметических операций. Например,

Допустим у нас есть программа суммирования чисел.

Некоторые компиляторы по умолчанию могут переписать код для использования нескольких АЛУ одновременно (будем считать, что n делится на 2):

Так как операции суммирования не ассоциативны, эти две программы могут выдать различный результат.

4.3 Числовые константы

Помните, что не все десятичные числа имеют двоичное представление с плавающей запятой. Например, число «0,2» будет представлено как «0,200000003» в одинарной точности. Соответственно, «0,2 + 0,2 ≈ 0,4». Абсолютная погрешность в отдельном
случае может и не высока, но если использовать такую константу в цикле, можем получить накопленную погрешность.

4.4 Выбор минимума из двух значений
4.5 Сравнение чисел

Очень распространенная ошибка при работе с float-ами возникает при проверке на равенство. Например,

Ошибка здесь, во-первых, в том, что 0,2 не имеет точного двоичного представления, а во-вторых 0,2 – это константа двойной точности, а переменная fValue – одинарной, и никакой гарантии о поведении этого сравнения нет.

Лучший, но все равно ошибочный способ, это сравнивать разницу с допустимой абсолютной погрешностью:

Недостаток такого подхода в том, что погрешность представления числа увеличивается с ростом самого этого числа. Так, если программа ожидает «10000», то приведенное равенство не будет выполняться для ближайшего соседнего числа (10000,000977). Это особенно актуально, если в программе имеется преобразование из одинарной точности в двойную.

Выбрать правильную процедуру сравнения сложно и заинтересованных читателей я отсылаю к статье Брюса Доусона. В ней предлагается сравнивать числа с плавающей запятой преобразованием к целочисленной переменной. Это — лучший, хотя и не портабельный способ:

5. Проверка полноты поддержки IEE754

Думаете, что если процессоры полностью соответствуют стандарту IEEE754, то любая программа, использующая стандартные типы данных (такие как float/double в Си), будет выдавать один и тот же результат на разных компьютерах? Ошибаетесь. На портабельность и соответствие стандарту влияет компилятор и опции оптимизации. Уильям Кэхэн написал программу на Си (есть версия и для Фортрана), которая позволяет проверить удовлетворяет ли связка «архитектура+компилятор+опции» IEEE754. Называется она «Floating point paranoia» и ее исходные тексты доступны для скачивания. Аналогичная программа доступна для GPU. Так, например, компилятор Intel (icc) по умолчанию использует «расслабленную» модель IEEE754, и в результате не все тесты выполняются. Опция «-fp-model precise» позволяет компилировать программу с точным соответствием стандарту. В компиляторе GCC есть опция «-ffast-math», использование которой приводит к несоответствию IEEE754.

Заключение

Напоследок поучительная история. Когда я работал над тестовым проектом на GPU, у меня была последовательная и параллельная версия одной программы. Сравнив время выполнения, я был очень обрадован, так как получил ускорение в 300 раз. Но позже оказалось, что вычисления на GPU «разваливались» и обращались в NaN, а работа с ними в GPU была быстрее, чем с обычными числами. Интересно было другое — одна и та же программа на эмуляторе GPU (на CPU) выдавала корректный результат, а на самом GPU – нет. Позже оказалось, что проблема была в том, что этот GPU не поддерживал полностью стандарт IEEE754 и прямой подход не сработал.

Сейчас арифметика с плавающей запятой почти совершенна. Практически всегда наивный подход сработает, и программа, не учитывающая все ее особенности, выдаст правильный результат, а описанные подводные камни касаются только экзотических случаев. Но нужно всегда оставаться бдительным: в таком вопросе как компьютерная математика легко наступить на грабли.

Источник

Автор: Яшкардин Владимир &nbsp &nbsp
www.softelectro.ru &nbsp &nbsp
Дата: 2009 &nbsp &nbsp &nbsp &nbsp
Редакция: 04.06.2012
info@softelectro.ru

§1. Название стандарта.

Данный стандарт разработан ассоциацией IEEE (Institute of Electrical and Electronics Engineers) и используется для представления действительных чисел (чисел с плавающей точкой) в двоичном коде. Наиболее используемый стандарт для вычислений с плавающей точкой, используется многими микропроцессорами и логическими устройствами, а также программными средствами.

В 2008 года ассоциация IEEE выпустила стандарт IEEE 754-2008, который включил в себя стандарт IEEE 754-1985.

§2.Краткое описание стандарта.

Стандарт содержит 23 страницы текста в 7 секциях и одном приложении: 1.Scope(Область применения) 1.1 Implementation Objectives (Описывает цели стандарта) 1.2 Inclusions (Описывает что включено в стандарт) 1.3 Exclusions (Описывает что не определяет стандарт) 2.Definitions (Вводимы определения) 3.Formats (Форматы чисел) 3.1 Sets of Values (Наборы переменных для представления формата) 3.2 Basic Formats (Базовые форматы) 3.3 Extended Formats (Расширенные форматы) 3.4 Combinations of Formats (Комбинирование форматов) 4.Rounding (Округления) 4.1 Round to Nearest (Округление к ближайшему) 4.2 Directed Roundings (Прямое округление) 4.3 Rounding Precision (Точность округления) 5.Operations (Операции) 5.1 Arithmetic (Арифметика) 5.2 Square Root (Квадратный корень) 5.3 Floating-Point Format Conversions (Конверсия форматов с плавающей точкой) 5.4 Conversion Between Floating-Point and Integer Formats (Конверсия между форматами с плавающими точками и форматами целых чисел.) 5.5 Round Floating-Point Number to Integer Value (округление чисел с плавающей точкой в целые числа) 5.6 Binary Decimal Conversion (Конверсия бинарного в десятичное) 5.7 Comparison (Сравнение) 6.Infinity, NaNs, and Signed Zero (Бесконечность, не числа, и знаковый ноль) 6.1 Infinity Arithmetic (Арифметические действия с бесконечностями) 6.2 Operations with NaNs (Операции с не числами) 6.3 The Sign Bit (Операции с знаковым бит) 7.Exceptions (Исключения) 7.1 Invalid Operation (Недопустимые операции) 7.2 Division by Zero (Деление на ноль) 7.3 Overflow (Переполнение) 7.4 Underflow (Нехватка разряда) 7.5 Inexact (Неточность) 8.Traps (Обнаружение недопустимых операций) 8.1 Trap Handler (Исполнитель обнаружения недопустимых операций) 8.2 Precedence (Первоочередность) A.Recommended Functions and Predicates (Рекомендованные функции и утверждения)

&nbsp &nbsp &nbsp &nbspК сожалению, организация IEEE превратилась из международной общественной инженерной организации (которой она была изначально) в торговую организацию.
Этой организации принадлежит авторское право на публикацию стандарта IEEE754-1985.
Поэтому если вы захотите ознакомиться, с оригиналом стандарта, вам придется купить его примерно за 80$.
Но, Российского законодательство разрешает мне в учебных целях комментировать данный стандарт.
Поэтому дальше я буду давать вольное изложение стандарта и выражать своё мнение о нём в учебных целях.

§3. Основные понятия в представлении чисел с плавающей точкой.


3.1 Представление числа в нормализованном экспоненциальном виде.


3.2 Представление числа в денормализованном экспоненциальном виде.


3.3 Преобразование десятичного числа в двоичное число с плавающей точкой.

Наша задача сводится к представлению десятичного числа с плавающей точкой, в двоичное число с плавающей точкой в экспоненциальном нормализованном виде. Для этого разложим заданное число по двоичным разрядам:

Приведем полученное число к нормализованному виду в десятичной и двоичной системе:
1,55625∙exp10 +2 = 1,0011011101∙exp2 +111

В результате мы получили основные составляющие экспоненциального нормализованного двоичного числа:
Мантиссу M=1,0011011101
Экспоненту exp 2= +111

§4. Описание преобразования чисел по стандарту IEEE 754.

4.1 Преобразование двоичного нормализованного числа в 32 битный формат IEEE 754

Основное применение в технике и программирование получили форматы 32 и 64 бита.
Например, в VB используют типы данных single (32 бита) и double (64 бита).
В Си аналогично используют float (32 бита) и double (64 бит)
Рассмотрим преобразование двоичного числа 10011011,101 в формат single-precision (32 бита) стандарта IEEE 754.
Остальные форматы представления чисел в IEEE 754 являются увеличенной копией single-precision.

Чтобы представить число в формате single-precision IEEE 754 необходимо привести его к двоичному нормализованному виду. В §3 мы проделали это преобразование над числом 155,625. Теперь рассмотрим, как двоичное нормализованное число преобразуется к 32 битному формату IEEE 754.

В результате десятичное число 155,625 представленное в IEEE 754 c одинарной точностью равно 431BA000 (hex).

4.2 Преобразования числа формата 32 бит IEEE 754 в десятичное число

Это целые числа которые записанные в числе IEEE 754 в двоичном виде.

Приведём формулу для получения десятичного числа из числа IEEE754 одинарной точности:

Проверяем наш пример:
F =(-1) 0 ∙2 (134-127) ∙(1+ 1810432 / 2 23 )= 2 7 ∙(1+0,2158203125)=128∙1,2158203125=155,625

§5. Формальное представление чисел в стандарте IEEE 754 для любого формата точности.

Рис. 1 Представление числа в формате IEEE 754

Формула вычисления десятичных чисел с плавающей точкой, из чисел представленных в стандарте IEEE754:

(Формула №1)

Используя формулу №1 вычислим формулы для нахождения десятичных чисел из форматов одинарной (32 бита) и двойной (64 бита) точности IEEE 754:

Рис.2 Формат числа одинарной точности (single-precision) 32 бита

Рис.3 Формат числа двойной точности (double-precision) 64 бита

§6. Представление денормализованного числа и других чисел в формате IEEE 754

Отсюда видно, что невозможно представить число нуль или бесконечность в заданном формате.

Поэтому формула №1 не применяется в следующих случаях:

Формула расчета денормализованных чисел:

(Формула №2)

7.2 Полный диапазон чисел одинарной точности (32 бит) по стандарту IEEE754


7.3 Полный диапазон чисел двойной точности (64 бит) по стандарту IEEE754


7.4 Точность представления вещественных чисел в формате IEEE754.

Числа представленные в формате IEEE754 представляют конечное множество, на которое отображается бесконечное множество вещественных чисел. Поэтому исходное число может быть представлено в формате IEEE754 с ошибкой.

Рис.6 Функция ошибки точности представления числа в IEEE754

Абсолютная максимальная ошибка для числа в формате IEEE754 равна в пределе половине шага чисел. Шаг чисел удваивается с увеличением экспоненты двоичного числа на единицу. То есть, чем дальше от нуля, тем шире шаг чисел в формате IEEE754 по числовой оси.

Шаг денормализованных чисел равен 2 (E-149) (Single) и 2 (E-1074) (Double).
Соответственно предел макс. абсолютной ошибки будет равен 1/2 шага числа: 2 (E-150) (Single) и 2 (E-1075) (Double).
Относительная ошибка в % будет равна: (2 (E-150) /F)*100%(Single) и (2 (E-1075) /F)*100% (Double).

Шаг нормализованных чисел равен 2 (E-150) (Single) и 2 (E-1075) (Double).
Соответственно предел макс. абсолютной ошибки будет равен 1/2 шага числа: 2 (E-151) (Single) и 2 (E-1076) (Double).
Относительная ошибка в % будет равна: (2 (E-151) /F)*100%(Single) и (2 (E-1076) /F)*100% (Double).

Максимальная относительная ошибка для денормализованного числа(single/double):

Максимальная относительная ошибка нормализованного числа(single):

Максимальная относительная ошибка нормализованного числа(double):

7.5 Общие сведенья для чисел одинарной и двойной точности стандарта IEEE 754.


§8. Округление чисел в стандарте IEEE 754.

Стандарт IEEE754 предусматривает четыре способа округления чисел.

§9. Проблемы компьютерных вычислений, вызванные использованием стандарта IEEE754.

Стандарт IEEE 754 широко применяется в технике и программировании.
Большинство современных микропроцессоров изготовляются с аппаратной реализацией представления вещественных переменных в формате IEEE754.
Язык программирования и программист не могут изменить эту ситуацию, иного преставления вещественного числа в микропроцессоре не существует.
Когда создавали стандарт IEEE754-1985 представление вещественной переменной в виде 4 или 8 байт казалось очень большой величиной, так как объём оперативной памяти MS-DOS был равен 1 Мб. А, программа в этой системе могла использовать только 0,64 Мб. Для современных ОС размер в 8 байт является ничтожным, тем не менее переменные в большинстве микропроцессоров продолжают представлять в формате IEEE754-1985.

Рассмотрим ошибки компьютерных вычислений, вызванные применением чисел в формате IEEE754.

9.1 Ошибки связанные с точностью представления вещественных чисел в формате IEEE754. Опасная редукция.

На самом деле ошибки точности представления числа наиболее безобидные в компьютерных вычислениях, и обычно многие программисты на них не обращают никакого внимания. Тем не менее они вас могут сильно огорчить.

9.2 Ошибки связанные с неправильным приведением типов данных. Дикие ошибки.

Эти ошибки вызваны тем, что исходное число представленное в формате single и в формате double обычно не равны друг другу.
Например: исходное число 123456789,123456789
Single: 4CEB79A3=+123456792,0(dec)
Double: 419D6F34547E6B75=+123456789,12345679104328155517578125
Разница между Single и Double составит:2,87654320895671844482421875

Вот пример на VB:
Относительная погрешность результата равна: &#8734 (бесконечности)
Такую ошибку называют «грязным нулем».
Если переменные привести к одному типу, то этой ошибки не будет.
Поэтому переменные и промежуточные результаты компьютерных вычислений должны быть приведены к одному типу данных.
Например, требование приведения данных к одному типу изложено в стандарте на язык Си ISO/IEC 9899:1999.

Обратите внимание на то, что недостаточно просто привести все исходные данные к одному типу. Необходимо привести также результаты промежуточных операций к одному типу.
Вот пример с ошибкой в промежуточном результате:

Здесь ошибка возникает потому, что промежуточный результат 1/3 в строке c=c-1/3 будет иметь тип double, а не single. Чтобы избавиться от ошибки вам надо привести промежуточный результат к типу single с помощью оператора приведения типов CSng. Пример приведения типа данных для GNU C, присланный Григорием Ситкаревым :

Если Вариант 1 (без приведения типов) выполнить с переменными двойной точности (double), то ошибки приведения данных не будет и Result=0.000000
Поэтому в большинстве случаев чтобы избавиться от приведения типов данных надо просто использовать тип данных double и забыть о существовании типа single(float).
Ошибки вычислений вызванные не приведением типов данных я называю «Дикими ошибками», так как они связаны с незнанием стандартов и теории программирования (т.е. с плохим фундаментальным образованием)

9.3 Ошибки вызванные сдвигом мантисс. Циклические дыры.

Эти ошибки связаны с потерей точности результата при неполном пересечении мантисс чисел на числовой оси.
Если мантиссы чисел не пересекаются на числовой оси, то операции сложения и вычитания между этими числами невозможны.
К примеру возьмём число Single: 47FFFFFF = +131071,9921875(dec)
В двоичной системе это число выглядит так: +11111111111111111,1111111

Покажем несколько компьютерных операций сложений и этим числом в формате Single
Значащих цифр в мантиссе двоичного числа в формате Single не более 24
Красным цветом показаны цифры выходящие за этот предел и не участвующие в формате Single

1. сложение с одинаковым числом (ошибка сдвига =0.0).

В последнем примере мантиссы чисел разошлись, и арифметические операции с этими числами становятся бессмысленными.

Как видно из приведенных примеров ошибка сдвига возникает если у исходных нормализованных чисел различаются экспоненты. Если числа отличаются более чем в 2 23 (для single) и 2 52 (для double), то операции сложения и вычитания между этими числами не возможны.
Максимальная относительная погрешность результата операции равна примерно 5,96e-6%, что не превышает относительную погрешность представления числа (см.п.9.1).

Хотя с относительной погрешностью здесь всё в порядке, здесь есть другие проблемы.
Во-первых, работать с числами можно только в узком диапазоне числовой оси, где мантиссы пересекаются.
Во-вторых, для каждого исходного числа существует предел выполнения цикла называемый «Циклической дырой». Поясню, если существует цикл в котором исходное число суммируется к сумме, то существует численный предел суммы для этого числа. То есть сумма достигнув определённой величины перестает увеличиваться от сложения её с исходным числом.

Как вы понимаете, такая система работает в бесконечном цикле.
Допустим в один из дней фасовочная машина простояла слишком долго и бункер заполнился до 300 кг.
Что произойдет после её включения?

Упрощенный пример работы цикла программы управления: В данном примере фасовочная машина забрала из бункера 100 кг продукции, а вес продукции в бункере не изменился.
Почему не изменился?
Потому, что мантиссы чисел 300 и 0,00001 не пересекаются для формата single.

Далее формовочная машина доведет вес бункера до 500 кг и остановится. Фасовочная машина заберет все таблетки из бункера и тоже остановится. Программа будет показывать вес в бункере 500кг. Прибегут специалисты, проверят датчики, провода, компьютер и скажут что программа зависла. Но, программа не зависала, она продолжает работать без сбоев и любой контроль это подтвердит. Просто число 0,0001 попало в циклическую дыру и выйти из него не может.

В результате нам крупно повезло, что это был фармацевтический цех, а не Саяно-Шушенская ГЭС.

На самом деле опытный программист никогда не будет делать циклическое вычитание(или суммирование) таким образом. Этот пример вымышлен специально, и так считать нельзя, хотя с точки зрения математика здесь всё безупречно. Эта ошибка свойственна математикам и начинающим программистам.
Я бы сказал, что основная работа программиста заключается в борьбе с погрешностями, а не в математических решениях поставленной задачи.

Привожу правильный пример решения этой задачи, любезно предоставленный Ситкаревым Григорием: Показанный выше пример взят из реального промышленного кода.
Для наглядности упростим выше приведенный пример.
Как видно из этого примера, программисту приходится вычислять погрешность результата в каждом цикле, чтобы учесть её в следующем цикле.
Обратите внимание, что программист должен быть абсолютно готов к тому, что некоторые основные понятия математики могут не выполняться при вычислениях в формате IEEE754. Например, правила алгебраической коммутативности (a + b) + с = (a + c) + b, обычно не выполняются при таких вычислениях.
К сожалению, в современном фундаментальном математическом образовании этому вопросу уделяют мало внимания, оставляя решения проблем инструментария на прикладного программиста.

9.4 Ошибки вызванные округлением. Грязный ноль.

При компьютерных вычислениях можно выделить два вида округления:
1. Результат выполненной арифметической операции всегда округляется.
2. Вывод и ввод вещественного числа в окно Windows происходит с округлением.

В первом случае переменная округляется по одному из 4-типов округления IEEE754, по умолчанию округление происходит к ближайшему целому.
При этом переменная принимает новое округлённое значение.
В п.9.2 мы рассматривали сложение двух одинаковых чисел:

1. сложение с одинаковым числом (ошибка сдвига =0.0).

Здесь результат операции сложения двух чисел абсолютно точен, но результат был округлен микропроцессором. Таким образом к точному результату была добавлена ошибка округления. В общем случае ошибка округления находится в пределах точности числа.

Во втором случае переменная не меняет своего значения, просто в окно Windows выводится округлённое значение вещественного числа. Получается, что исходная переменная и её отображение в окне Windows это разные числа. Это не ошибка формата IEEE754, это ошибка Windows.
Для переменных типа Single в окне Windows отображается 7 значащих цифр округлённых до ближайшего целого.
3DFCD6EA =+0,12345679104328155517578125 в окне отображается как 0,1234568
Для переменных типа Double в окне Windows отображается 15 значащих цифр округлённых до ближайшего целого.
3FBF9ADD3746F67D=+0,12345678901234609370352046653351862914860248565673828125 отображается как 0,123456789012346

Очень часто эта ошибка возникает в интерфейсе «оператор-машина».
Например, при обнулении тары в весовых программах.

Результат выполнения программы приведенного выше примера

9.5 Ошибки на границе норма/денорма числа. Числа убийцы.

Эти ошибки возникают при работе с числами находящимися на границе нормализованного/денормализованного представления чисел. Они связанны с различием в представление чисел в формате IEEE754 и в различии формул перевода формата IEEE754 в вещественные числа. То есть устройства (или программы) должны применять различные алгоритмы в зависимости от положения вещественного числа на числовой оси формата. Кроме того, что это приводит к усложнению устройств и алгоритмов, ещё возникает неопределённость переходной зоны. Неопределённость переходной зоны заключается в том, что стандарт не определяет конкретного значения границы перехода. По сути дела граница перехода находится между двумя вещественными числами:
Последним денормализованным числом 000FFFFFFFFFFFFF:
Точное десятичное значение этого числа:
+2,2250738585072008890245868760858598876504231122409594654935248025624400092282356951787758888037591552642309780950
4343120858773871583572918219930202943792242235598198275012420417889695713117910822610439719796040004548973919380791
9893608152561311337614984204327175103362739154978273159414382813627511383860409424946494228631669542910508020181592
6642134996606517803095075913058719846423906068637102005108723282784678843631944515866135041223479014792369585208321
5976210663754016137365830441936037147783553066828345356340050740730401356029680463759185831631242245215992625464943
0083685186171942241764645513713542013221703137049658321015465406803539741790602258950302350193751977303094576317321
0852507299305089761582519159720757232455434770912461317493580281734466552734375e-308

и первым нормализованным числом 0010000000000000:
Точное десятичное значение этого числа:
+2,2250738585072013830902327173324040642192159804623318305533274168872044348139181958542831590125110205640673397310
3581100515243416155346010885601238537771882113077799353200233047961014744258363607192156504694250373420837525080665
0616658158948720491179968591639648500635908770118304874799780887753749949451580451605050915399856582470818645113537
9358049921159810857660519924333521143523901487956996095912888916029926415110634663133936634775865130293717620473256
3178148566435087212282863764204484681140761391147706280168985324411002416144742161856716615054015428508471675290190
3161322778896729707373123334086988983175067838846926092773977972858659654941091369095406136467568702398678315290680
984617210924625396728515625e-308
Так как граница является вещественным числом, то её точность можно задавать до бесконечности и цифровому устройству или программе может не хватить разрядности для принятия решения к какому диапазону отнести данное число.

§10 Заключение.

Из сказанного выше видно, что мнение о том, что при вычислениях с плавающей точкой результат не выходит за пределы относительной погрешности представления наибольшего числа является ложным. Ошибки перечисленные в п.9 складываются друг с другом. Такие ошибки как грязный ноль и опасная редукция могут сделать погрешность вычислений неприемлемой. Особое внимание при программировании компьютерных вычислений программист должен обратить на результаты близкие к нулю.

Некоторые специалисты считают, что этот формат чисел представляет угрозу человечеству.
Вы можете прочитать об этом в статье IEEE754-тика угрожает человечеству &nbsp
Хотя многие факты из этой статьи излишне драматизированы, и возможно неправильно интерпретированы, но проблема компьютерных вычислений философски отражена правильно.

Я не сторонник драматизации вычислений по стандарту IEEE754. Стандарт работает с 1985 года и полностью вошел в стандарт IEEE754-2008, который расширил точность вычислений. Но, проблема достоверности компьютерных вычислений сегодня очень актуальна, и стандарт IEEE754-2008 и рекомендации ISO не решили эту проблему. Я думаю, в этой области нужна инновационная идея, которой разработчики стандарта IEEE754-2008 к сожалению не обладают.

Если ученые(которые придумывают новое) и специалисты (которые знают как пользоваться известным) не могут решить проблему, то нужна инновация.

Можно представлять вещественные числа, как числа с фиксированной запятой. Для представления всего диапазона чисел Double достаточно иметь переменную состоящую из 1075 битов целой части и 1075 битов дробной части, т.е. около 270 байт на одну переменную. При этом все числа будут представлены с одинаковой абсолютной точностью. Можно работать с числами во всем диапазоне числовой оси, то есть становится возможным суммировать большие числа с малыми числами. Шаг чисел по числовой оси будет равномерен, то есть числовая ось будет линейна. Тип данных будет только один, т.е. не нужны целые, вещественные и др. типы. Здесь возникает проблема реализации регистров микропроцессоров размерностью в 270 байт, но это не проблема для современной технологии.

Для написания п.9 мне пришлось создать программу которая представляет числа в виде переменной с фиксированной точкой, длиною 1075,1075 байтов. Где число можно представить в виде строки символов ASCII, то есть один символ равен одному числовому разряду. Так же пришлось написать все арифметические операции при работе со строками ASCII. Это программа является аналогом бумажного расчета. Так как математические способности микропроцессора в ней не используются, то считает она довольно медленно. Зачем я это сделал?
Я не смог найти программы, которая смогла бы точно представить число формата IEEE754 в десятичном виде.
Так же я не нашел программы (хотя они безусловно есть, в чём нет сомнений) где в окно можно ввести 1075 значащих десятичных цифр.

Вот к примеру точно десятичное значение числа double 7FEFFFFFFFFFFFFF:
+17976931348623157081452742373170435679807056752584499659891747680315726078002853876058955 863276687817154045895351438246423432132688946418276846754670353751698604991057655128207624 549009038932894407586850845513394230458323690322294816580855933212334827479782620414472316 8738177180919299881250404026184124858368,0

Вы можете воспользоваться программой IEEE754 v.1.0 &nbsp
для изучения и оценки погрешностей при работе с вещественными числами представленными в формате IEEE754.

Список литературы:
1. IEEE Standard for Binary Floating-Point Arithmetic. Copyright 1985 by The Institute of Electrical and Electronics Engineers, Inc 345 East 47th Street, New York, NY 10017, USA

Источник

Читайте также:  приправа шафран для каких блюд подходит
Сказочный портал