"Hi, Amigo!"

"Hi, Bilaabo!"

"I want to tell you a little about different numbering systems."

"You've already heard that people use the decimal system. Here are the main facts of this system:

**1)** 10 digits are used to write numbers: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9.

**2)** The number 543 means 5 hundreds + 4 tens + 3 ones.

"This is equivalent to writing 5*100 + 4*10 + 3*1, which can be written as 5*10^{2} + 4*10^{1} + 3*10^{0}.

Note that thousands, hundreds, tens and ones are powers of the number 10.

**1)** One is 10 to the zeroth power.

**2)** Ten is 10 to the first power.

**3)** One hundred is 10 to the second power.

**4)** One thousand is 10 in the third power, etc.

"Yep. Got it."

"But now imagine that we only have 8 digits. Then we have the octal system. Here are its main facts:"

**1)** 8 digits are used to write numbers: 0, 1, 2, 3, 4, 5, 6, 7.

**2)** The number 543_{8} means 5*8^{2}+4*8^{1}+3*8^{0}. In other words, it's 5*64 + 4*8 + 3*1 = 320+32+3 = 320+32+3=355_{10}

**I wrote 8 and 10 as subscripts to indicate how many digits are used to represent the number.**

"I think I get it. I think I could convert a number from the octal system to decimal. But I probably couldn't go the other way."

"It's not so difficult. Imagine you need to use several trucks to move a pile of sand. You have dump trucks, ordinary trucks, and very small trucks. But the trucks can't go if they're not full."

"How would you do it?"

"First, I would fill up dump trucks, since they're the biggest. Then, when I saw that there wasn't enough sand to fill the truck, I would switch to the smaller vehicles. And then the even smaller ones."

"It's actually very similar here. Let's try to convert the number 355_{10} back to octal."

"First, we divide it by 64 (8^{2}) and get 5 with a remainder of 35. This means that the first digit of our number is 5. Then we divide the remainder by 8 (8^{1}) and get 4 with a remainder of 3. Thus, we get the number 543_{8}."

"By the way, you can also move in the other direction. After all, 543_{8} == 5*64+4*8+3 == ((5)*8+4)*8+3. Our octal "tens" and "hundreds" must be divided by 8. Hence, the remainder of division by 8 will be our octal digits."

"First, let's divide 355 by 8. We get 44 with a remainder of 3. That is, 355=44*8+3. And 44 can be represented as 5*8+4. Thus, 355= (5*8+4)*8+3; Here are our digits: 5, 4, 3. The number we're looking for is 543_{8}."

"I think I get it, but I'll need to practice a little to understand everything all the way."

"Programming often involves using numbers with different bases (i.e. the number of digits used in the numbering system). The most popular are 2, 8, 10, 16, and 64."

"But why is this necessary? Why do we need numbers represented by 2, 8, 16, or 64 digits?"

"It's about how the processor works internally. Very simplistically, if current is flowing through a wire, then we say that it's value is 1; if there is no current, then its value is 0. All numbers are stored in memory cells. These cells have a very basic design. And they can only store 0 or 1."

"But such simplification (only 0 or 1) made it possible to make elements inside the processor and memory very small. Modern processors and memory modules include billions of different elements. And their area is often no more than a square centimeter."

"Whoa. Now I know."

"Now we turn to binary numbers. Here we have the same thing as with octal, only easier."

**1)** 2 digits are used to write numbers: 0, 1.

**2)** The number 101_{2} means 1*2^{2} + 0*2^{1} + 1*2^{0}. In other words, it's 1*4+0*2+1*1 =4+1=51_{10}

"Yes. I remember. One cell, which can have a value of either 0 or 1, is called a bit. But it can't store very much information, so they are combined into groups of 8. These groups are called bytes."

"Exactly. A byte is a group of eight bits. It can store the following values: 00000000, 00000001, ... 11111111. These values correspond to the decimal numbers 0,1, ... 255. Which gives us a total of 256 values."

What's the largest integer in Java? Or rather what is its type?

"A long. A long consists of 8 bytes. In other words, 64 bits. It can store values from -2^{63} up to 2^{63}-1.

"Yep. I won't touch on how to convert numbers from decimal to binary or vice versa. Otherwise, the lesson would be too long."

"Instead, let's talk a little more about the hexadecimal system."

"Yes, it's very interesting. For the binary and octal systems, we simply got rid of digits, starting with two and eight, respectively. But what do we do here? Add new digits?"

"Exactly! Look at this:"

**1)** 16 digits are used to write numbers: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, F.

**2)** The number 543_{16} means 5*16^{2} + 4*16^{1} + 3*16^{0}. In other words, it's 5*256+4*16+3*1 = 1280+64+3 = 1347_{10}

"So, we just added letters as digits? O_o"

"Yep. And what's the big deal? Why invent new numbers when letters work perfectly well? Check it out:"

Hexadecimal digit | Decimal value |
---|---|

0 | 0 |

1 | 1 |

8 | 8 |

9 | 9 |

A | 10 |

B | 11 |

C | 12 |

D | 13 |

E | 14 |

F | 15 |

"I'm also not going to talk about converting from decimal to hexadecimal. But here's one interesting fact. A hexadecimal digit is represented by exactly 4 bits, with values from 0 to 15. So, one byte can be written with eight binary digits (0 or 1) or two hexadecimal digits."

"Here's an example:"

Decimal number | Binary number | Hexadecimal number |
---|---|---|

0 | 0000 0000 | 00 |

1 | 0000 0001 | 01 |

15 | 0000 1111 | 0f |

16 | 0001 0000 | 10 |

31 | 0001 1111 | 1f |

32 | 0010 0000 | 20 |

128 | 1000 0000 | 80 |

129 | 1000 0001 | 81 |

255 | 1111 1111 | ff |

"The hexadecimal representation is easily converted to binary (and vice versa). That's why the internal byte representation of a number is rarely given in binary (using 0s and 1s) in programming. That would be too long and difficult to understand. Hexadecimal notation is much more readable and compact."

"I agree. Even I liked it."

"By the way, Java lets you write numbers in various numbering systems directly in the code:"

Base | Distinguishing feature | Examples | Invalid numbers |
---|---|---|---|

2 | 0b at the beginning of the number | 0b00001111 | 0b1111121 |

8 | 0 at the beginning of the number | 01234343 | 0128 |

10 | None | 95459 | 909a |

16 | 0x at the beginning of the number | 0x10ff | 0x1cgh |

"Excellent lesson. Thank you, Bilaabo."

GO TO FULL VERSION

"First, we divide it by 64 (8^2) and get 5 with a remainder of 35. This means that the first digit of our number is 5. Then we divide the remainder by 8 (8^1) and get 4 with a remainder of 3. Thus, we get the number 543."How do you know to start this process with 8^2, instead of 8^3 or 8^4 or 8^1? What is it about the number 355 in base-10, when converting to base-8, that says the starting exponent is 2? Or is it just "always start with exponent 2" no matter what? That doesn't make any sense to me, maybe it is that the exponent to start with is the number of digits in the first number minus 1? In the next lesson one of the tasks is converting 6 in base-10 to base-2. I cannot figure out how apply the above process to this problem. If we start with base^0 (i.e. the number of digits in 6, minus 1), then we take 6/(2^0) = 6 remainder 0. That's not getting me anywhere. Okay, so maybe it really is "always start with exponent 2"? If I do it that way, then it's 6/(2^2) = 1 remainder 2. 1 is the first digit. Then 2/(2^1) = 1 remainder 0, so the second digit is 1. And I guess when you are left with a number less than the base, that's the final digit? So this worked. I'm still not convinced "always start with exponent 2" is correct, it seems so nonsensical. Let's try converting 1500 in base-10 to base-2. So to start, we have 1500/(2^2), which is 375 remainder 0, but of course that can't be a digit in base-2, so yes, this shows that "always start with exponent 2" is not correct. Please CodeGym come back and explain how you know which exponent to start the process with.