So far we have considered that in binary representation you have all the positions you want (like when you write on paper, you can always add more digits).
Now we will consider the condition that you only have a fixed number of digits. This introduces a new problem: the overflow problem, which is what happens when you exhaust the available capacity.
Overflow occurs when the number we are trying to represent is greater than the maximum value that can be stored in the given container. In this case, the variable overflows and goes back to 0.
The overflow problem is not unique to the binary system. It also happens to you, for example, if you have a combination lock that only has 4 digits. When you go past 9999
, you will return to 0000
.
In binary, you will continuously encounter the overflow problem. Because, in general, your binary number will be stored in “some part” of the computer’s memory (that memory has a size, and if you exceed it… 💥BANG, overflow).
On the other hand, overflow is not catastrophic “per se”. That is, it won’t make your computer explode, nor will anything break. Simply, the number you had stored will quietly and silently return to zero.
Of course, if you were using that number to count something… well frankly, it might not be good (if it was your WoW player’s level, you will go back to the beginning. If it’s a plane, it might be worse and crash to the ground).
But overflow is not bad. In fact, it is inevitable and even necessary in many processes. You just have to understand it, keep it in mind, and learn to control it.
Example of Overflow
Unsigned Overflow
Let’s imagine we want to store the number 300
in decimal in a binary number. But, we only have 8 bits.
In binary, the number 300
in decimal is 1 0010 1100
in binary. We would need 9 digits to store it. But since we only have 8 digits, the maximum we can store is 255 in decimal.
Therefore, if we keep increasing from 0 to 300, when we reach 255, the counter will reset to 0.
Let’s look at it step by step:
Step | Binary | Decimal | Comment |
---|---|---|---|
0 | 0000 0000 | 0 | Starting |
1 | 0000 0001 | 1 | |
2 | 0000 0010 | 2 | |
… | … | Continuing up | |
255 | 1111 1111 | 255 | Reached maximum |
256 | 0000 0000 | 0 | Overflowed |
… | … | Continuing up | |
300 | 0010 1100 | 44 |
The stored result will be 0010 1100
in binary, which is 44 in decimal. This is the same number that we would have converted to binary and removed the bits that do not fit (1 0010 1100
in this example, the 1
on the left).
Signed Overflow
If the number was signed (that is, it has a sign) the problem is even worse. Continuing with the same example, let’s assume we only have 8 bits. But now, since it is a signed variable, the limits are -128 to 127.
If I want to store the number 300, it’s not just that it barely doesn’t fit… it doesn’t fit even in two times 127!
Let’s also look at it step by step:
Step | Binary | Decimal | Comment |
---|---|---|---|
0 | 0000 0000 | 0 | Starting |
1 | 0000 0001 | 1 | |
2 | 0000 0010 | 2 | |
… | … | Continuing up | |
127 | 0111 1111 | 127 | Maximum positive |
128 | 1000 0000 | -128 | Switch to negatives |
129 | 1000 0001 | -127 | |
… | … | Continuing up | |
255 | 1111 1111 | -1 | Maximum negative |
256 | 0000 0000 | 0 | Overflowed |
… | … | Continuing up | |
300 | 0010 1100 | 44 |
Just like in the unsigned case, we ended up with a positive number 44
. But, along the way, we passed through all the negatives from -128 to 0 (which, if we don’t have it controlled, can be a real problem).
Handling Overflow
We have said that the most important thing is to understand overflow and know how to manage it. Overflow is influenced by:
- The number of bits we are managing (8, 16, 32, 64…)
- Whether our variable is signed or unsigned
In both cases, when we add one to our number, the binary number will increase. When it reaches its capacity limit, it will reset to zero.
As we have seen, it is even more complicated if the stored number represents a signed number. Because the available range will be much smaller (half minus one), and before overflowing, it will go through the entire range of negative numbers.
To avoid overflow when storing binary numbers in fixed-length containers, we must always keep in mind the range of values we expect to handle and choose the appropriate data size.
In programming environments, it is common to use data types with specific sizes (like uint8, int16, etc.) that guarantee a valid range of values and help us prevent unwanted overflows.
Additionally, when performing arithmetic operations, it is important to check the data limits to avoid a calculation resulting in a value outside the allowed range.