The glyphs used, in increasing value, are 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, and F. The table in Figure 1 illustrates the relationship between decimal, binary, and hexadecimal expressions.
|0||0||00h||16||1 0000||10h||32||10 0000||20h|
|1||1||01h||17||1 0001||11h||33||10 0001||21h|
|2||10||02h||18||1 0010||12h||34||10 0010||22h|
|3||11||03h||19||1 0011||13h||35||10 0011||23h|
|4||100||04h||20||1 0100||14h||36||10 0100||24h|
|5||101||05h||21||1 0101||15h||37||10 0101||25h|
|6||110||06h||22||1 0110||16h||38||10 0110||26h|
|7||111||07h||23||1 0111||17h||39||10 0111||27h|
|8||1000||08h||24||1 1000||18h||40||10 1000||28h|
|9||1001||09h||25||1 1001||19h||41||10 1001||29h|
|10||1010||0Ah||26||1 1010||1Ah||42||10 1010||2Ah|
|11||1011||0Bh||27||1 1011||1Bh||43||10 1011||2Bh|
|12||1100||0Ch||28||1 1100||1Ch||44||10 1100||2Ch|
|13||1101||0Dh||29||1 1101||1Dh||45||10 1101||2Dh|
|14||1110||0Eh||30||1 1110||1Eh||46||10 1110||2Eh|
|15||1111||0Fh||31||1 1111||1Fh||47||10 1111||2Fh|
Figure 1 – Decimal, binary, and hexadecimal expression comparison
Now it’s time to talk about the part we all hate – the rules. Actually, they’re pretty simple in hex.
When writing a hex expression, bear in mind that we must break our life-long habit of moving to the next column upon reaching 9 in the first column. In hex, our first column tops out at F – if we want to increase the expressed value by one, we then end up with 10h, which is equivalent to 16 decimal. I know that this can be very confusing to the uninitiated. The first time I saw numeric expressions with letters as digits, I was lost … until I discovered the secret of hex numbers. Now, I find it very sensible and logical, but I still think it looks odd!
The columns in a hex expression are valued in powers of 16, with the right-most column being 16^0, the next column to the left being 16^1, the third column being 16^2, and so on to the extent of the expression. This being the case, let’s look at the expression 0378h. This value breaks down as follows:
|0 x 16^3 = 0 x 4096 =||0|
|3 x 16^2 = 3 x 256 =||768|
|7 x 16^1 = 7 x 16 =||112|
|8 x 16^0 = 8 x 1 =||8|
If we add all of these values, we arrive at a decimal value of 888, which is in fact the decimal equivalent of 0378h. Got it yet? OK – let’s look at something practical now.
In a PC, COM1: is assigned to the base I/O address of 03F8h. The serial port requires a range of eight I/O addresses in sequence. If that is the case, what it the highest I/O address that COM1: will use? If we just count sequentially through the eight hex addresses starting at 03F8h, we will end up at 03FFh … 03F8, 03F9, 03FA, 03FB, 03FC, 03FD, 03FE, and 03FF. Where are these addresses located in relation to the installed memory in the PC? They are right at the top of the first kilobyte of physical RAM – 03F8h is 1016 decimal, and 03FFh is 1023 decimal. Don’t forget that we start numbering things at 0 in computers, so that first kilobyte will be bytes 0 through 1023. See how it works?
Converting Hex to Decimal
There are two common methods of converting hex values to decimal values. One of them has already been demonstrated. In this method, all that you need is a powers of sixteen table and a calculator. This is the method that I prefer if I must manually convert, as there is less to remember. This method simply requires you to multiply the value in each column by the appropriate power of 16 for that column. Record each of the products as you determine it, and then add them all together to get the decimal expression for the original hex value.
The next method requires you to first convert each digit to decimal. Start with the left-most digit, and multiply its decimal value by sixteen. Record the product as a subtotal and move on to next digit to the right. For each column to which you advance (except the right-most column), you would first convert that column’s digit to its decimal equivalent, add that value to your running subtotal, and then multiply the new subtotal by sixteen and record this value as your newest subtotal. Keep on doing this – convert, add, and multiply until you get to the last (right-most) column, where the routine changes. For this column, once you have converted it to decimal and added it to your running subtotal, stop – you’re finished. Clear as mud, right? Let’s try it … let’s convert D809F3h to decimal. In the steps below, the running subtotal is shown in red, and the values in parentheses are decimal equivalents for hex digits.
By using this method, we arrive at D809F3h being equivalent to 14158323 decimal. This method works, but it requires that you remember the steps and follow them faithfully. I find it confusing when compared to the method that I used earlier. Let’s apply that method to this hex value, to see if it gives us the same result – which, obviously, it should. Using the first conversion method, we get the following:
|D x 16^5 = 13 x 1048576 =||13631488|
|8 x 16^4 = 8 x 65536 =||524288|
|0 x 16^3 = 0 x 4096 =||0|
|9 x 16^2 = 9 x 256 =||2304|
|F x 16^1 = 15 x 16 =||240|
|3 x 16^0 = 3 x 1 =||3|
End result: both methods work. Now that we’ve got that out of the way – and that we know how to manually convert hex values to decimal values, I’ll let you in on a secret. Remember I said earlier “if I must manually convert…”? That implies that there are other ways, and so there are.
One of them is a hex-to-decimal convertor available through the web. Check it out – it’s pretty neat. This convertor performs direct conversion of any three-digit hex value into its decimal equivalent, and works directly in your browser, kind of like a mileage finder in a road atlas. If the hex value is larger than three digits, there is an auxiliary table for converting four- and five-digit values. We will talk more about another (and easier) conversion method later on.
Converting Decimal to Hex
When it comes to manually converting a decimal value into its hexadecimal equivalent, there is a method that is basically the reverse of one of our hex-to-decimal conversion methods. Here’s how to do it. Start by dividing the original decimal value by sixteen, resulting in a quotient and a remainder. Set the quotient aside, and then convert the remainder to hex – and remember, it will be less than sixteen. This converted value becomes the right-most digit in the new hex expression. If there is no remainder, the right-most hex digit will be a zero. Now divide the quotient by sixteen and repeat the above process to arrive at the next hex digit. This digit gets placed to the left of the first one. Keep on doing this divide by sixteen and convert the remainder routine until you arrive at a zero quotient. Whatever remainder you now have gets converted to hex and becomes the left-most hex digit in the expression.
Let’s try it out by converting 2135 decimal to its hex equivalent. The hex digits arrived at in each step are shown in red.
|2135 divided by 16 = 133, R7||7h|
|133 divided by 16 = 8, R5||57h|
|8 divided by 16 = 0, R8||857h|
In this example, the remainders were all less than ten, so their decimal values and their hex values were the same. As can be seen, this manual conversion method works the way it should, and resulted in the calculated hex equivalent of 2135 decimal being 857h.