Понимание записи дополнения до двух

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

Возьмем дополнение числа до двух. Если у нас есть неотрицательное число, записанное в двоичном представлении, например, 0000 0101 (5), мы можем переписать число в дополнении до двух, выполнив следующие действия.

1. Используйте побитовый оператор НЕ, чтобы перевернуть все биты

2. Наш номер теперь можно записать как 1111 1010

3. Далее мы должны добавить к результату 1

4. Наш новый номер, записанный в дополнении до двух, выглядит как 1111 1011 (-5)

Выражение значений со знаком в нотации дополнения до двух имеет два основных преимущества:

  1. Выполнение основных арифметических операций (сложение, вычитание и умножение) над дополнительным числом до двух — это точно такой же процесс, как и для неотрицательных двоичных чисел. Кроме того, схемы сложения и вычитания могут быть унифицированы, если отрицательные числа выражены в виде дополнения до двух. То есть каждый раз, когда мы выполняем операции (сложение или вычитание) над дополнительным числом двойки, мы всегда складываем.

Например, на скриншоте ниже мы вычитаем 12-69. Если мы перепишем 69 в дополнительной нотации до двух, мы можем просто сложить числа вместе, используя двоичное сложение, чтобы получить окончательный результат -57.

Если, однако, мы попытаемся выразить отрицательные числа, не помещая их в два комплимента, например. «-1» в двоичном формате как 10000001 поначалу может показаться более интуитивным. Проблемы возникают, когда мы пытаемся выполнить двоичное сложение.

Например, если мы попытаемся сложить 2 + (-1):

00000010 + 10000001 получаем = 10000011 что равно -3 правильно?

Неправильный. Простое сложение в этом случае не сработает, так как старший бит (MSB) в 10000001 по-прежнему равен нулю. Это означает, что 10000011 будет считаться положительным числом и будет равняться 129 или 0x81 в шестнадцатеричном формате.

Однако, если мы установим MSB равным «1» и представим число в дополнительном обозначении до двух, мы получим желаемый результат 1.

00000010 + 11111111 = 1.

Чтобы быть предельно точным, давайте вспомним, что целое число составляет 4 байта, и для того, чтобы установить MSB равным «1», мы должны установить самый левый бит самого левого байта. В шестнадцатеричном формате число, выраженное выше как 11111111, будет записано как 0xFFFFFFFF, где каждая буква «F» представляет полубайт (четыре бита), установленный в «1111» в двоичном формате. Следовательно, в двоичном формате наш -1 выражается как: 1111 1111 1111 1111 1111 1111 1111 1111.

2. Выражение отрицательных чисел в дополнении до двух устраняет проблему двойного нуля.

Например, если бы мы полагались на выражение отрицательных чисел в нотации дополнения, у нас было бы как знаковое, так и беззнаковое представление нуля. То есть как 10000000, так и 00000000 могут использоваться для представления -0 и 0 соответственно. Если бы это было так, каждое приложение должно было бы убедиться, что любое ненулевое целое число также не равно отрицательному 0.

Однако, поскольку компьютеры используют дополнение до двух для выражения отрицательных чисел, 10000000 или 0x80 фактически представляют число 128.