Теория:
Учитывая использование для отрицательных чисел дополнительного кода, операции сложения и вычитания сводятся к одной операции сложения.
Рассмотрим на примере двух чисел \(A\) и \(B\) все возможные операции и получим значение \(A + B\), \(A - B\) и \(B - A\). Действия будем проводить в восьмиразрядной сетке.
Пример \(1\)
Выполни действия над числами \(A\) и \(B\), получи значение машинного кода суммы чисел \(A\) и \(B\).
Пусть \(A = 71\); \(B = 36\).
1. Получим прямой код чисел \(A\) и \(B\) в восьмиразрядной сетке.
2. ; .
3. Выполним поразрядное сложение:
Ответ:
Пример \(2\)
Выполни действия над числами \(A\) и \(B\), получи значение машинного кода суммы чисел \(A\) и \(B\).
Пусть \(A = 120\); \(B = 116\).
1. Получим прямой код чисел \(A\) и \(B\) в восьмиразрядной сетке.
2. ; .
3. Выполним поразрядное сложение.
\(0\) | \(1\) | \(1\) | \(1\) | \(1\) | \(0\) | \(0\) | \(0\) | |
\(+\) | \(0\) | \(1\) | \(1\) | \(1\) | \(0\) | \(1\) | \(0\) | \(0\) |
\(1\) | \(1\) | \(1\) | \(0\) | \(1\) | \(1\) | \(0\) | \(0\) |
4. Проанализируем полученный результат. Так как сумма представлена восемью разрядами, а в старшем разряде \(1\), то по правилам записи числа мы получили отрицательную сумму. Причина ошибки в том, что сумма исходных чисел «переполняет» допустимый диапазон чисел со знаком в восьмиразрядной сетке (\(120 + 116 = 236\), диапазон [\(-128\); \(127\)]).
Для обнаружения этой ошибки воспользуемся следующим приёмом.
1) Добавим к каждому из чисел ещё один разряд, дублирующий знаковый.
0 | \(0\) | \(1\) | \(1\) | \(1\) | \(1\) | \(0\) | \(0\) | \(0\) |
0 | \(0\) | \(1\) | \(1\) | \(1\) | \(0\) | \(1\) | \(0\) | \(0\) |
0 | \(1\) | \(1\) | \(1\) | \(0\) | \(1\) | \(1\) | \(0\) | \(0\) |
2) Как видим, при сложении только знаковых разрядов должен получиться \(0\), по факту сложения получили \(1\). Разница и указывает на наличие ошибки.
3) Вывод таков. Данные числа надо складывать в сетке с бόльшим количеством разрядов.
\(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(1\) | \(1\) | \(1\) | \(1\) | \(0\) | \(0\) | \(0\) | |
\(+\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(1\) | \(1\) | \(1\) | \(0\) | \(1\) | \(0\) | \(0\) |
\(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(0\) | \(1\) | \(1\) | \(1\) | \(0\) | \(1\) | \(1\) | \(0\) | \(0\) |
5. , вычисления в десятичной системе подтверждают полученный результат.
Ответ:
Пример \(3\)
Выполни действия над числами \(A\) и \(B\), получи значение машинного кода разности чисел \(B\) и \(A\).
1. Получим прямой код числа \(B\) в восьмиразрядной сетке:
.
2. Получим дополнительный код числа \(A\) в восьмиразрядной сетке:
3. Выполним поразрядное сложение.
\(0\) | \(0\) | \(1\) | \(0\) | \(0\) | \(1\) | \(0\) | \(0\) | |
\(+\) | \(1\) | \(0\) | \(1\) | \(1\) | \(1\) | \(0\) | \(0\) | \(1\) |
\(1\) | \(1\) | \(0\) | \(1\) | \(1\) | \(1\) | \(0\) | \(1\) |
Оценим полученный результат. Согласно приёму с дублированием знакового разряда, ошибки в вычислениях нет (см. Пример \(2\).) Так как операция выполняется в восьмиразрядной сетке, единица в самом старшем разряде обозначает, что получено отрицательное число, и это его дополнительный код.
Определим .
Отнимем от числа единицу и инвертируем его:
.
4. Вычисления в десятичной системе счисления подтверждают полученный результат.
Ответ:
Практически для операции сложения применяют рекурсивный алгоритм, использующий операцию сдвига и прибавление единицы.
Сдвиг влево в любой системе счисления равносилен умножению на основание системы счисления.
Рис. \(1\). Сдвиг влево
Сдвиг вправо равносилен делению нацело на основание системы счисления.
Рис. \(2\). Сдвиг вправо
В зависимости от чётности слагаемых и (или вычитаемых) выполняются следующие тождества:
и чётные:
и нечётные:
чётное, нечётное:
нечётное, чётное:
В соответствии с этими тождествами сложение \(= 14\) и \(= 16\) будет выглядеть как
\((((1 + 1 × 2) × 2 + 1) × 2 + 1) × 2 = 30.\)
Примечание. С учётом рекурсивного спуска к этой формуле пришли так:
\((14 + 16) = (7 + 8) × 2 = ((3 + 4) × 2 + 1) × 2 = (((1 + 2) × 2 + 1) × 2 + 1) × 2 = (((1 + 1 × 2) × 2 + 1) × 2 + 1) × 2.\)
Если обозначить команды:
1. \(+\) \(1\),
2. \(×\) \(2\),
то получение \(30\) из \(1\), а по сути сложение \(14\) и \(16\), будет записано следующей последовательностью: \(2121212\).
1. \(+\) \(1\),
2. \(×\) \(2\),
то получение \(30\) из \(1\), а по сути сложение \(14\) и \(16\), будет записано следующей последовательностью: \(2121212\).
Источники:
Рис. 1. Сдвиг влево. © ЯКласс.
Рис. 2. Сдвиг вправо. © ЯКласс.