There is another aspect to binary arithmetic that you need to understand - negative numbers. So far we have assumed everything is positive - the optimist's view if you will - our glass is still half full. But we can't avoid the negative side of life forever - the pessimist's perspective that our glass is already half empty. How do we indicate a negative number? Well, we only have binary digits at our disposal and indeed they contain the solution.
For numbers that we want to have the possibility of negative values (referred to as signed numbers) we must first decide on a fixed length (in other words, the number of binary digits) and then designate the leftmost binary digit as a sign bit. We have to fix the length in order to avoid any confusion about which bit is the sign bit as opposed to bits that are digits. A single bit is quite capable of representing the sign of a number because a number can be either positive - corresponding to a sign bit being 0, or negative - indicated by the sign bit being 1.
Of course, we can have some numbers with 8 bits, and some with 16 bits, or whatever, as long as we know what the length is in each case. If the sign bit is 0 the number is positive, and if it is 1 it is negative. This would seem to solve our problem, but not quite. If we add -8 in binary to +12 we would really like to get the answer +4. If we do that simplistically, just putting the sign bit of the positive value to 1 to make it negative, and then doing the arithmetic with conventional carries, it doesn't quite work:
since +8 is 0000 1000. If we now add these together we get:
This seems to be -20, which is not what we wanted at all. It's definitely not +4, which we know is 0000 0100. Ah, I hear you say, you can't treat a sign just like another digit. But that is just what we do have to do when dealing with computers because, dumb things that they are, they have trouble coping with anything else. So we really need a different representation for negative numbers. Well, we could try subtracting +12 from +4 since the result should be -8:
For each digit from the fourth from the right onwards we had to borrow 1 to do the sum, analogously to our usual decimal method for subtraction. This supposedly is -8, and even though it doesn't look like it, it is. Just try adding it to +12 or +15 in binary and you will see that it works. So what is it? It turns out that the answer is what is called the two's complement representation of negative binary numbers.
Now here we are going to demand a little faith on your part and avoid getting into explanations of why it works. We will just show you how the 2's complement form of a negative number can be constructed from a positive value, and that it does work so you can prove it to yourself. Let's return to our previous example where we need the 2's complement representation of -8. We start with +8 in binary:
We now flip each digit - if it is one make it zero, and vice versa:
This is called the 1's complement form, and if we now add 1 to this we will get the 2's complement form:
Now this looks pretty similar to our representation of -8 we got from subtracting +12 from +4. So just to be sure, let's try the original sum of adding -8 to +12:
So the answer is 4 - magic! It works! The carry propagates through all the leftmost 1's, setting them back to zero. One fell off the end, but we shouldn't worry about that. It's probably the one we borrowed from off the end in the subtraction sum we did to get -8. In fact what is happening is that we are making the assumption that the sign bit, 1 or 0, repeats forever to the left. Try a few examples of your own, you will find it always works quite automatically. The really great thing is, it makes arithmetic very easy (and fast) for your computer.