Вы находитесь на странице: 1из 22

Модуль 7.

Представление числовых данных в компьютере


Особенностью представления чисел в компьютере является
использование двоичной системы счисления для их представления и
ограниченное количество разрядов для их хранения, ограниченность
диапазона. Обычно числа располагаются в памяти компьютера в двоичном
формате в последовательных ячейках памяти, минимальный набор
двоичных ячеек, к которому мы можем обратиться по адресу, составляет 8
бит, 1 байт (Рис. 1).

Рис. 1

Для иллюстрации основных принципов хранения чисел в памяти


компьютер будем использовать примеры программ на языках Си и Python
(для просмотра примеров необходим компилятор gcc и интерпретатор
python 3).

Хранение в компьютере целых чисел без знака (unsigned)


Диапазон беззнаковых значений в 8-битной сетке показан на рисунке
Рис. 2.

Рис. 2

Представление чисел является циклически повторяющимся,


цикличность представления целых чисел в ограниченной разрядной сетке
можно изобразить с помощью круговой диаграммы, эта диаграмма наглядно
иллюстрирует переход к следующему числу и явление переполнения (Рис.
3).

Рис. 3
Представление целых неотрицательных чисел (unsigned) не
отличается от канонической формы представления двоичных чисел, и
называется прямым кодом (Рис. 4).

Рис. 4

В языке Си (как и во многих других) используется несколько целых


типов данных, различающихся размером, диапазон легко определить из
соотношения (5):

Xmax =2k–1, (5)


где k – количество разрядов.
Значения разных типов для языков программирования зависят от
специфики реализации. Для определения, сколько места занимает в памяти
компьютера переменная того или иного типа unsigned языка Си и какое
максимальное значение может принимать число, хранимое в переменной
этого типа можно использовать пакет limits.h, который включает
определения характеристик общих типов переменных (Рис. 5).

Рис. 5

Типичное значение 64-битной программы показано на рисунке Рис. 6, а


различные значения диапазона в зависимости от разрядности в Таблица 1.
Таблица 1
X
K Xmax Типы данных
min
8 0 255 unsigned char (Си)

16 0 65 535 unsigned short (Си)

32 0 4 294 967 295 unsigned int (Си)


unsigned long (Си)
64 0 18 446 744 073 709 551 615
unsigned long long (Си)
Рис. 6

Целые числа со знаком. Дополнительный код


При хранении целых чисел в двоичной форме записи самый левый
(старший) бит отводится под знак («знаковый бит»). Если знаковый бит
равен 0, то, значит, мы имеем дело с положительным числом, если в
знаковом бите стоит «1», то мы имеем дело с отрицательным числом.
Далее, в зависимости от этого бита, действуют разные алгоритмы. Для
положительных чисел используется прямой код, а для отрицательных
используется дополнительный код.
При K-битном кодировании дополнительный (two’s complement) код
отрицательного числа –X равен двоичному коду числа 2K – X (дополнение
до 2K).
Например, для 4-битного представления: код числа «–X» равен
двоичному коду числа 16 – X (дополнение до 16). Код числа -1 равен
двоичному коду числа 16 – 1 = 15 =11112. В двоичной арифметике для
компьютера должно выполняться правило, что дополнительный код
положительного числа, сложенный с дополнительным кодом отрицания
этого же числа, должен давать в сумме 0 (Рис. 7).

Рис. 7

Для 8-битных чисел: код числа «–X» равен двоичному коду числа 256 –
X (дополнение до 256). -1 = 111111112 (Рис. 8).

Рис. 8

Алгоритм №1 построения дополнительного кода для -X:


1. перевести число X в двоичную систему счисления, в двоичном
написании дополнить это число спереди нулями до n-разрядного
представления;
2. построить обратный код, выполнив инверсию всех битов (заменить 0
на 1 и наоборот);
3. к результату добавить 1, отбросить выходящий за пределы n-
разрядов результат.
Примеры построения дополнительного кода для 4-битного числа -6 и 8-
битного числа -70 показаны на рисунке Рис. 9.

Рис. 9

Алгоритм №2 построения дополнительного кода для -X:


1. перевести число X в двоичную систему счисления;
2. Копируем последовательность справа налево, пока не будет
переписана младшая единицы, оставшуюся последовательность
инвертируем.
Примеры построения показаны на рисунке Рис. 10.

Рис. 10

Диапазон значений в 8-битной сетке показан на рисунке Рис. 11.


Рис. 11

Также как и для беззнаковых, представление чисел является


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

Рис. 12

Диапазон определяется из соотношений (6):

Xmin =–2k-1 и Xmax =2k-1–1, (6)


где k – количество разрядов.

Рис. 13

Как уже было сказано выше, значения разных типов для языков
программирования зависят от специфики реализации. Для определения,
сколько места занимает в памяти компьютера переменная того или иного
типа и какое максимальное значение может принимать число, хранимое в
переменной этого типа можно использовать пакет limits.h, который
включает определения характеристик общих типов переменных (Рис. 13).
Типичное значение 64-битной программы показано на рисунке Рис. 14,
а различные значения диапазона в зависимости от разрядности в Таблица
2.

Рис. 14
Таблица 2

K X X Типы данных
min max

char (Си)
8 – 128 127
short (Си)
16 – 32 768 32 767
int (Си)
32 – 2 147 483 648 2 147 483 647
long (Си)
64 – 263 263 – 1
long long (Си)
Одна и та же кодовая комбинация может обозначать различные числа,
в зависимости от типа, от того как ее интерпретировать – как знаковую или
беззнаковую (Рис. 15).

Рис. 15

В Python 3 размер целого числа ограничивается только объемом


памяти компьютера.
Операции с целыми числами
Цикличность представления и ограниченность диапазона приводит к
тому, что итогом операции может возникнуть выход за границу диапазона
представимых значений, т.е. переполнение разрядной сетки.
Посмотрим на примере для 4-битного представления. Для 4-битного
представления знакового представления – диапазон от -8 до 7, для
беззнакового от 0 до 15. В примере на рисунке Рис. 16, если слагаемые
интерпретировать как беззнаковые, то выход за границу диапазона не
произошло, а для знаковых 9 превышает максимальное значение.

Рис. 16

В примере на рисунке Рис. 17 выход за диапазоны в обоих случаях.

Рис. 17

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


сложить два отрицательных или положительных числа (Рис. 17).

Рис. 18

Примеры для 8-битного представления изображены на рисунке Рис. 19.


Рис. 19

Для выявления выхода за границы представимого диапазона


используется флаг – бит переноса в регистре состояний процессора CF,
сигнализирует о беззнаковом переполнении 32-битная (Рис. 20).

Рис. 20

Для выявления выхода результата операции за границы представимого


диапазона в регистре состояний имеется еще один флаг – бит
арифметического переполнения OF. При выполнении действий АЛУ
устанавливает этот бит в 1, если при интерпретации операндов как
знакопеременных, результат операции выйдет за границы представимого
диапазона (Рис. 21).
Рис. 21

Поразрядные операции
Поразрядные операции выполняются с отдельными битами числа и не
влияют на остальные. Рассмотрим эти операции в Си и Python. Побитовые
операции (кроме сдвига вправо) не зависят от того, знаковый операнд или
без знака.
Операция «НЕ» (инверсия ~).

Рис. 22

Операция «И» (конъюнкция &), с помощью этой операции можно


установить в нуль определенные биты (Рис. 23).
Рис. 23

Операция «ИЛИ» (дизъюнкция |), с помощью этой операции можно


записать единицу в определенные биты (Рис. 24).

Рис. 24

Операция «Исключающее или» (сложение по mod 2, ^), с помощью


этой операции можно инвертировать определенные биты (Рис. 25).
Рис. 25

Операции сдвига >> и <<, первый операнд содержит значение, которое


нужно сдвинуть, второй – указывает, на сколько разрядов нужно сдвинуть
значение первого операнда.
При сдвиге влево младшая часть всегда заполняется нулями,
независимо от знака операнда (Рис. 26, Рис. 28).

Рис. 26

При сдвиге вправо беззнаковых целых старшая часть всегда


заполняется нулями, логический сдвиг (Рис. 27).

Рис. 27
Рис. 28

При сдвиге вправо знаковых целых старшая часть всегда заполняется


значением старшего (знакового) разряда, такой сдвиг носит название
арифметического сдвига (Рис. 29).
Рис. 29

Сдвиг влево (вправо) – это быстрый способ умножения


(целочисленное деления с округлением «вниз», к ближайшему меньшему
целому) положительного числа на 2 (Рис. 30).

Рис. 30

Хранение вещественных чисел


Для представления действительных чисел в компьютерах
используется формат с плавающей запятой (точкой) [1]. В 2008 года
ассоциация IEEE выпустила стандарт IEEE 754-2008, который включил в
себя стандарт IEEE 754-1985. Этот стандарт определяет представление и
операции для чисел с плавающей точкой в компьютерных системах,
рассматривает форматы хранения, правила арифметики (в том числе и
правила округления), стандартные и расширенные функции для типов
одинарной (single), двойной (double), расширенной (extended) и
расширяемой (extendable) точности, а также рекомендует форматы для
обмена данными. В рамках используемых форматов определяет:
 как представлять нормализованные положительные и отрицательные
числа с плавающей запятой;
 как представлять денормализованные положительные и
отрицательные числа с плавающей запятой;
 как представлять «нулевые» числа;
 как представлять специальные величины «плюс бесконечность» и
«минус бесконечность» (±∞);
 как представлять специальные величины «не число» (NaN, NaNs, not
a number).
Класс нормализованных чисел позволяет решить проблему
неоднозначного представления чисел с плавающей запятой и задачу
представления чисел в широком диапазоне значений. Перед записью в
машинное слово действительное число приводится к нормализованному
виду.
Числа с плавающей запятой в общем случае можно представить в
экспоненциальном виде:

A =±Z  BP, (6)


где Z – мантисса, всегда в прямом коде с опущенным неявным битом, B –
основание системы счисления, а P – показатель степени в формате со
смещением.
Нормализованная форма: значащая часть Z удовлетворяет условию 1
≤ Z < B, где B – основание системы счисления (стандарт IEEE 754).
Примеры перехода к нормализованной форме в двоичной системе
счисления показаны на рисунке Рис. 31.

Рис. 31
Нормализованное число содержит в мантиссе ровно один разряд в
целой части, он отличен от 0, а порядок находится в допустимых пределах,
определяемых разрядностью поля порядка.
Ненормализованное число может содержать в целой части мантиссы
более одного разряда, отличного от 0, или ни одного, такое число можно
нормализовать, если оно не выйдет за границы разрядной сетки, при
нормализации возможна потеря точности.
Денормализованное число – число, которое в данных разрядностях
мантиссы и порядка невозможно нормализовать (поскольку величина
слишком мала).
В компьютере число с плавающей точкой, согласно стандарту,
хранится в виде, показанном на рисунке Рис. 32.

Рис. 32

Точность задается количеством битов в поле мантиссы, диапазон


задается количеством битов в поле порядка, оно определяет насколько
можно сдвигать разделитель. Порядок, показатель степени хранится в
формате со смещением, это еще один вариант хранения целочисленных
значений. Соответствующие двоичным наборам значения смещаются на
2𝑘−1 − 1, т.е. из значения вычитается смещение. Например, для 3-битного
представления смещение равно 23−1 − 1 = 3 (Таблица 3).
Таблица 3
Значени Значения для формата
Набор битов
я со смещением
000 0 -3
001 1 -2
010 2 -1
011 3 0
100 4 1
101 5 2
110 6 3
111 7 4
Для получения фактического значения показателя нужно вычесть сдвиг
из хранимой степени.
Начнем рассмотрение на примере, в котором для хранения числа
будем использовать 1 байт памяти, хотя в машинах, конечно, используются
более длинные коды. В старшем бите хранится знак, на порядок отведем 3
бита, на мантиссу 4. Определим, какое число представляет следующий
набор бит 01000110. Старший бит отвечает за знак, раз в нем 0,
следовательно, число положительное. Порядок 100, как было сказано
выше, хранится в формате со смешением, для 3-битного представления
смешение равно 3 и, следовательно, показатель степени равен 4 – 3 = 1.
Мантисса всегда в прямом коде с опущенным неявным битом 1,0110 и,
следовательно, такой битовый набор хранит число 1,0112 ∙ 21 = 10,112 =
2,75 (Рис. 33).

Рис. 33
𝑘−1
Формула для расчета ±2𝑃−2 +1 (1 + 𝑍) ∙ 2−𝑛 , где k – количество битов
порядка, n – количество битов мантиссы.

Рис. 34

Представим число -0,375 в уменьшенном учебном 8-битном формате с


плавающей точкой. Сначала переведем число в двоичную систему
счисления и нормализуем. Так как число отрицательное, то старший бит
будет равен 1. Для представления порядка необходимо к -2 прибавить
смещение и перевести в двоичную систему и получим искомый набор бит
(Рис. 34).

Рассмотрим проблему, которая возникает, когда мы попытаемся


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

Рис. 35

Переводим число в двоичную систему счисления, нормализуем,


получаем 5 знаков после запятой и для одного знака разряда не хватает. В
результате получаем последовательность, которая является
представлением числа 6,25.То, что произошло, называется ошибкой
усечения (округления), и означает, что часть числа потеряна, потому что в
мантиссе не хватило разрядов (Рис. 35).

Рис. 36
Рассмотрим примеры представления в 32-х битном формате IEEE754,
представим число 13,375. В таком формате на порядок отводится 8 битов и
23 бита на мантиссу. Смещение для порядка равно 28−1 − 1 = 127.

Первым шагом число переводим в двоичную систему счисления,


нормализуем, представляем порядок в формате со смещением, удобно
записывать в более компактной шестнадцатеричной записи (Рис. 36).

Рис. 37

В примере на рисунке Рис. 37, при переводе в двоичную систему


получили периодическую дробь.

Минимальное и максимальное нормализованные числа (абсолютные) в


32-х битном формате IEEE754 представлены на рисунке Рис. 38.

Рис. 38

При нормализованном представлении чисел возникает проблема,


связанная с отсутствием нуля. В нормализованных числах нуль не входит в
интервал значений мантиссы. Это обстоятельство не позволяет получить
нулевой результат вычислений. В IEEE754 предусмотрено представление
для специальных чисел, работа с которыми вызывает исключение.
На рисунке Рис. 39 изображены представления для +0 и -0.

Рис. 39

На рисунке Рис. 40 изображены представления для +∞ и -∞.

Рис. 40

Представления на рисункеРис. 41 не считаются числами (NAN), кроме


случая +∞ и -∞, к ним относятся символы, или результаты недопустимых
операций, X обозначает 0 или 1.

Рис. 41
Рис. 42

Денормализованные числа – это числа, мантиссы которых лежат в


диапазоне 0.1 <= M <1. Представление демонормлизованных чисел
показана на рисунке Рис. 42, за исключением +0 и -0.

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


𝑘−1
вид: ±2𝑃−2 +2 ∙ 𝑍 ∙ 2−𝑛 , где k – количество битов порядка, n – количество
битов мантиссы.
Полный диапазон чисел в 32-х битном формате IEEE754 изображен на
рисунке Рис. 43.

Рис. 43

Аналогично определяется для чисел с двойной точностью. Согласно


стандартам, типы float, double и long double для языка Cи являются
базовыми. Компилятором для них, как правило, отводится 4, 8 и 16 байт или
32, 64, 128 бит соответственно. Значения зависят от специфики
реализации, а для определения, сколько места занимает в памяти
компьютера переменная и какое максимальное значение может принимать
число c с плавающей запятой, сколько битов отводятся на мантиссу и
порядок можно использовать пакет float.h, который cодержит макросы,
определяющие различные ограничения и параметры типов с плавающей
точкой.

Рис. 44

Специальные числа бесконечность и неопределенность для языка Си в


таблице Таблица 4, примеры получения таких чисел приведены на рисунке
Рис. 45.
Таблица 4
Печатается Означает

1.#INF Положительная бесконечность


-1.#INF Отрицательная бесконечность
1.#IND Положительная неопределённость
-1.#IND Отрицательная неопределённость
Рис. 45

В Python три типа значений с плавающей точкой встроенные типы float,


complex и тип Decimal стандартной библиотеки, float предоставляет числа с
плавающей точкой двойной точностью диапазон значений, которых зависит
от компилятора языка Си применявшегося для компиляции интерпретатора
(Рис. 46). Если вам действительно необходимо обеспечить высокую
точность можно использовать числа типа decimal.Decimal.

Рис. 46

Вам также может понравиться