基数10の位取りによって表現された数を10進数と呼び、 基数2の場合は2進数と呼ぶことは前回説明しました。 この他にも、基数8の場合の 8進数 ( octal number ) と、基数16の場合の 16進数 ( hexadecimal number ) が使われます。
8進数では、右から1の位、8の位、64の位、512の位、…となります。 16進数では、右から1の位、16の位、256の位、4096の位、…となります。
8進数は、数字0から7までを使って表現されます。 16進数は、数字0から9までと、英字AからFまでを使って表現されます。 英字については、A は 10, B は 11, C は 12, D は 13, E は 14, F は 15 です。
なお、このような文脈で単に20と書きますと、これが10進数なのか8進数なのか16進数なのか分からなくなります。 この混乱を避けるため、8進数を表すときは左側に0を追加する慣習があります。 この慣習に従いますと、020は10進数で16になります。 16進数の場合は、左側に0xを追加します。 すると、0x20は10進数で32になります。
ここで、10進数、2進数、および16進数を相互に変換する方法について説明します。 10進2進の相互変換は前回説明しましたので、2進16進の相互変換ができれば、すべての変換ができます。
2進数を16進数に変換するには、次のようにします。
10進数 | 2進数 | 16進数 |
---|---|---|
0 | 0000 | 0 |
1 | 0001 | 1 |
2 | 0010 | 2 |
3 | 0011 | 3 |
4 | 0100 | 4 |
5 | 0101 | 5 |
6 | 0110 | 6 |
7 | 0111 | 7 |
8 | 1000 | 8 |
9 | 1001 | 9 |
10 | 1010 | A |
11 | 1011 | B |
12 | 1100 | C |
13 | 1101 | D |
14 | 1110 | E |
15 | 1111 | F |
16進数を2進数に変換するには、表の逆方向に置き換えます。
10進数では、負数は -3 のように符号(-)と絶対値(3)を組み合わせて表現します。 2進数で負数を表現する方法には、絶対値表現と補数表現があります。 絶対値表現 ( sign and magnitude notation ) は、符号ビットと負数の絶対値を組み合わせるものです。 補数表現 ( complement notation ) には、1の補数と2の補数があります。 1の補数 ( 1's complement ) とは、絶対値の2進数(1バイトならば左に0を追加して8桁にする)のすべてのビットを反転させたものです。 2の補数 ( 2's complement ) とは、1の補数に1を足したものです。 通常のシステムでは2の補数が使われます。
負数を扱わない場合と、2の補数で負数を表した場合で、表現できる数の範囲は次のようになります。
バイト数 | ビット数 | 表現できる数 (負数無し) |
表現できる数 (負数あり) |
---|---|---|---|
1バイト | 8ビット | 0〜255 | -128〜127 |
2バイト | 16ビット | 0〜65535 | -32768〜32767 |
4バイト | 32ビット | 0〜4294967295 | -2147483648〜2147483647 |
例題1. 10進数 -20 を1バイトの16進数に変換してください。 負数の表現は2の補数を用います。
解答例1.
10進数 -20 の絶対値 20 を2進数に変換します。
10進数 20 は2進数で 10100 です。
0 0 0 1 0 1 0 0(左に0を追加して1バイトにした) 1 1 1 0 1 0 1 1(ビットを反転させて1の補数にした) 1 1 1 0 1 1 0 0(1を足して2の補数にした)
したがって、10進数 -20 は1バイトの16進数で 0xec です。
2の補数による16進数を10進数に変換するには、上記の逆の操作を行います。
例題2. 1バイトの16進数 0xe7 を10進数に変換してください。 負数の表現は2の補数を用います。
解答例2.
1 1 1 0 0 1 1 1(2進数にした) 1 1 1 0 0 1 1 0(1を引いて1の補数にした) 0 0 0 1 1 0 0 1(ビットを反転させた)
1バイトの16進数 0xe7 の絶対値は2進数で 11001 です。
2進数 11001 は10進数で 25 です。 したがって、1バイトの16進数 0xe7 は10進数で -25 です。
2の補数の利点は、整数の符号を気にせずに四則演算が行えることです。 1バイトの足し算なら、右から9桁目以上を無視すれば、負数でも正しく計算ができます。 実際、- y の2の補数が 11111111 - y + 1 であることに注意しますと、
x + (-y の2の補数) = x + 11111111 - y + 1 = 11111111 + 1 + x - y = 100000000 + x - y
となり、右から9桁目以上を無視すれば、 x + - y の計算が正しく行えます。
なお、計算結果の桁数が越えることを オーバーフロー ( overflow ) と言います。
例題3. 10進数の足し算 49 + -11 = 38 を2進数で行ってください。 負数の表現は2の補数を用います。 始めに 49 と -11 を1バイトの2進数に変換し、2進数の足し算を行った後、結果を10進数に変換します。
解答例3.
10進数 49 は2進数で 110001 です。
10進数 11 は2進数で 1011 です。
0 0 0 0 1 0 1 1(左に0を追加して1バイトにした) 1 1 1 1 0 1 0 0(ビットを反転して1の補数にした) 1 1 1 1 0 1 0 1(1を足して2の補数にした)
したがって、10進数 -11 は1バイトの2進数で 11110101 です。
1 1 0 0 0 1 + 1 1 1 1 0 1 0 1 ------------------- 1 0 0 1 0 0 1 1 0
和の、右から9桁目以上を取り除いた2進数 100110 を、10進数に変換します。
2進数 100110 は10進数で 38 です。
問1. 10進数 -35 を1バイトの16進数に変換してください。 負数の表現は2の補数を用います。
問2. 1バイトの16進数 0xc4 を10進数に変換してください。 負数の表現は2の補数を用います。
問3. 10進数の足し算 43 + -17 = 26 を2進数で行ってください。 負数の表現は2の補数を用います。 始めに 43 と -17 を1バイトの2進数に変換し、2進数の足し算を行った後、結果を10進数に変換します。
今日の演習3の答案をメールで提出してください。 メールの差出人は学内のアドレス(b04a001@twcu.ac.jpなど)とし、メールの宛先はkonishi@twcu.ac.jpとします。 メールの本文には、学生番号、氏名、科目名、授業日(10月14日)を明記してください。