After you have learned how to convert decimal numbers into the binary system in Python Course #4: Binary Numbers, you will now see how to add and subtract binary numbers and how to represent negative numbers in the binary system.

## Adding Binary Numbers

Adding two binary numbers works in the same way as you would add two decimal numbers on paper. To add two decimal numbers by hand, you first write one number over the other such that the digit positions align:

\[\begin{array}{cr} & 2345 \\ +& 189 \\\hline \end{array}\]Then you start adding each digit position individually. In this example, the first digits are 5 and 9, which results in 14. The 4 will be written under the two digits that you just added together. The 1 of the 14 is added to the result of the next digits:

\[\begin{array}{cr} & 2345 \\ & 189 \\ +& \quad_1\hspace{0.5em}\\\hline & 4 \end{array}\]The next column of digits is 4, 8, and 1, which sums up to 13. Again the 3 is written under the digits just added, and the one is carried over to the next digit:

\[\begin{array}{cr} & 2345 \\ & 189 \\ +& \quad_1\hspace{0.2em}_1\hspace{0.5em}\\\hline & 34 \end{array}\]Repeat this procedure until you run out of digits to add together:

\[\begin{array}{cr} & 2345 \\ & 189 \\ +& \quad_1\hspace{0.2em}_1\hspace{0.5em}\\\hline & 2534 \end{array}\]In the end, you can read the result at the bottom of your calculation.

Adding two binary numbers together works the same way, but instead of using the \(+\) you use XOR \(\oplus\) to add the digits together. As introduced in Python Course #3: Introduction to Boolean Algebra, the \(\oplus\) is only 1 if the operands have different values. Let’s add the numbers 10 and 12 in binary together. First you have to convert 10 and 12 to binary which is \(10_{10} = 1010_2\) and \(12_{12} = 1100_2\). Then write one number under the other one such that the bits align:

\[\begin{array}{cr} & 1010 \\ \oplus& 1100 \\\hline \end{array}\]Now start with adding the first two digits on left \(0 \oplus 0 = 0\):

\[\begin{array}{cr} & 1010 \\ \oplus& 1100 \\\hline & 0 \end{array}\]Then add the second and the third column, which will both result in 1 because each time the digits are different:

\[\begin{array}{cr} & 1010 \\ \oplus& 1100 \\\hline & 110 \end{array}\]In the last column are two 1 which results in 0. However, when two 1 are added together, they will generate a carry-bit. Because \(1_{10} + 1_{10} = 2_{10} = 10_2\). The carry-bit is written under the next column of bits:

\[\begin{array}{cr} & 1010 \\ & 1100 \\\ \oplus& \hspace{0.01em}_1\quad\quad \\\hline & 0110 \end{array}\]This carry-bit is then added together with two zeros (leading zeros are not written down) \(0\oplus 0 \oplus 1 = 1\):

\[\begin{array}{cr} & 1010 \\ & 1100 \\\ \oplus& \hspace{0.01em}_1\quad\quad \\\hline & 10110 \end{array}\]The result of this addition is \(10110_2 = 22_{10} = 10_{10} + 12_{10}\). You can also check that the result is correct with the following Python code:

1
2
3
4

x = 0b1010
y = 0b1100
z = x + y
print(f"{z} = {z:b}")

## Negative Binary Numbers

Before you can start subtracting binary numbers, let’s first talk about representing negative values in the binary system.

### Ones’ Complement

«««< HEAD The ones’ complement or just complement of a binary number is the negation of every bit, and when you remember Python Course #3: Introduction to Boolean Algebra, the negation \(\neg\) will turn every 0 into 1 and every 1 into a 0. This ones’ complement can be used as a negative representation of a binary number. It allows you to represent numbers ranging from \(-(2^{N-1}-1)\) to \(2^{N-1}-1\) where \(N\) is the number of bits (or digits) of a binary number. Let’s take a look at 8-bit numbers: ======= The ones’ complement or just complement of a binary number is the negation of every bit. When you remember Python Course #3: Introduction to Boolean Algebra, the negation \(\neg\) will turn every 0 into 1 and every 1 into a 0. This ones’ complement can be used as a negative representation of a binary number. It allows you to represent numbers ranging from \(-(2^{N-1}-1)\) to \(2^{N-1}-1\) where \(N\) is the number of bits (or digits) of a binary number. Let’s take a look at 8-bit numbers:

main

bits | non-complement | ones’ complement |
---|---|---|

`0111 1111` | 127 | 127 |

`0111 1110` | 126 | 126 |

`0000 0010` | 2 | 2 |

`0000 0001` | 1 | 1 |

`0000 0000` | 0 | 0 |

`1111 1111` | 255 | -0 |

`1111 1110` | 254 | -1 |

`1111 1101` | 253 | -2 |

`1000 0001` | 129 | -126 |

`1000 0000` | 128 | -127 |

Here you can spot one very odd thing, and that is negative zero. This negative zero is because the ones’ complement states that the negative of a number is every bit negated. A number system involving two representations of one number leads to problems because exceptional cases have to be respected for operations involving this number.

### Twos’ Complement

Another way of representing negative numbers in binary is the twos’ complement. The twos’ complement takes the ones’ complement of a number and then adds a one. Before you can get the negative number for \(10_{10} = 1010_2\) lets think about the number of bits that are necessary to represent all values. With \(N\) bits \(2^N\) values can be represented. When only postive numbers are used the numbers from \(0\) to \(2^N\) can be displayed in binary using \(N\) bits. However, when you only got \(N\) bits, a part of the \(2^N\) representable values must be used for negative numbers. For the ones’ and twos’ complement representation, half of the values are used for negative numbers. For example, if you got 4 bits you can repesent positive values from \(0\) to \(7_{10} = 0111_2\). So if you want to represent values up to \(15_{10} = 01111_2\) you have to add a bit.

Now it’s time to get the twos’ complement negative representation of \(10_{10} = 01010_2\):

\[\begin{array}{cr} \neg & 01010 \\\hline & 00101 \\ \oplus& 1 \\\hline & 10110 \end{array}\]Adding a one to the ones’ complement avoids a negative 0 from the ones’ complement. When you got 5 bits to store your numbers, zero is represented as \(00000_2\) negating all bits results in \(11111_2\) and when you now add a single one to it and discard all bits that come after the fifth position, you will get \(00000_2\) again:

\[\begin{array}{cr} \neg & 00000 \\\hline & 11111 \\ & 1 \\ \oplus& \hspace{0.1em}_1\hspace{0.1em}_1\hspace{0.1em}_1\hspace{0.1em}_1\hspace{0.1em}_1\hspace{0.5em} \\\hline & \cancel{1}00000 \end{array}\]This means the “negative” representation of 0 in the twos’ complement is the zero itself.

Now take a look at the 8-bit numbers in two’s complement:

bits | non-complement | ones’ complement | |
---|---|---|---|

`0111 1111` | 127 | 127 | |

`0111 1110` | 126 | 126 | |

`0000 0010` | 2 | 2 | |

`0000 0001` | 1 | 1 | |

`0000 0000` | 0 | 0 | |

`1111 1111` | 255 | -1 | |

`1111 1110` | 254 | -2 | / |

`1111 1101` | 253 | -3 | |

`1000 0001` | 129 | -127 | |

`1000 0000` | 128 | -128 |

Adding a one to any binary number in twos’ complement will result in the correct successor number, which wasn’t the case for the ones’ complement due to the negative zero. Another nifty property of the twos’ complement is that the last bit on the left-hand side, also called the most significant bit (MSB), of every negative number is 1. This means you can identify a negative number by only looking at the MSB. The twos’ complement can represent the numbers from \(-2^{N-1}\) to \(2^{N-1}-1\) which is one number more than the ones’ complement.

## Subtracting Binary Numbers

Now that you know how to represent negative numbers in the binary system with the twos’ complement, subtracting numbers binary numbers from one another can be achieved pretty easily. Because subtraction can be interpreted as addition with a negative number:

\[a - b = a + (-b)\]To subtract \(12_{10} = 01100_2\) from \(10_{10} = 01010_2\) in binary you first have to convert \(12_{10} = 01100_2\) into its twos’ complement (carry-bits not shown):

\[\begin{array}{cr} \neg & 01100 \\\hline & 10011 \\ \oplus& 1 \\\hline & 10100 \end{array}\]Now the twos’ complement of \(12_{10}\) which is \(10100_2\) can be added to \(10_{10} = 01010_2\) (carry-bits not depicted):

\[\begin{array}{cr} & 01010 \\ \oplus& 10100 \\\hline & 11110 \end{array}\]The result of this addition is a negative number because the MSB is 1. But how do you figure out what negative number? You get the twos’ complement of it because:

\[-(-a) = a\]The twos’ complement of \(11110_2\) is \(00010_2 = 2_{10}\).

Subtracting binary numbers from each other concludes this article. You’ve learned how to add binary numbers using \(\oplus\), how to represent negative numbers with the twos’ complement, and how to subtract binary numbers from each other. I encourage you to add and subtract binary numbers to get more practice because doing things yourself is one of the best ways to learn.

If you have any questions about this article, feel free to join our Discord community to ask them over there.