ビットのシフト演算とはデータのビットの並びを右や左にシフトすることを言う。このための演算子がJavaでは揃っている。IoT時代になるにつれて、必要な知識になっていくだろう。
このページではシフト演算子の使い方についてまとめた。参考にしていただきたい。
目次
シフト演算子の使い方
Javaのシフト演算子は、ビットのシフト演算を行う演算子だ。ビットのシフト演算とは、データのビットの並びをまとめて右や左にシフトすることだ。シフトする方向だけでなくシフトするビットの数を指定することもできる。4ビット右にシフトする演算では、データの並びがすべて指定された右方向に4ビットずれる。
シフト演算子によって数値はどうなるか? 1ビット左にシフトするごと数値は2倍になる。1ビット右にシフトするごとに数値は半分になる。4ビット右シフトさせると、8分の1値になる。つまり、数値16を4ビット右シフトさせると、2になるということだ。
まずは、演算子の種類から見ていこう。
演算子の種類
シフト演算子には、3つの種類がある。次のセクションでこれらのひとつひとつの演算子の詳細を説明している。
- 左シフト演算子 <<
- 符号付右シフト演算子 >>
- 符号無し右シフト演算子 >>>
では、その詳細を見てみよう。
左シフト演算子 <<
シフト演算子「<<」は整数のビットを左にシフトする。演算子「<<」のオペランド1のビットをオペランド2の数だけシフトする。
書き方の基本は簡単だ。
演算結果 = オペランド1 << オペランド2;
ビットが左にシフトされると、右端のビットはどうなるかというと、0で埋められていく。左端のビットは、捨てられていく。
オペランド1がint型であれば、オペランド2の範囲は0から31になる。また、オペランド1がlong型であれば、オペランド2の範囲は0から63になる。
符号付右シフト演算子 >>
シフト演算子「>>」は、整数のビットを右に符号を付けてシフトする。>>演算子のオペランド1のビットをオペランド2の数だけシフトする。
書き方の基本は簡単だ。
演算結果 = オペランド1 >> オペランド2;
ビットが右にシフトされると、左端のビットはどうなるだろうか。符号付、つまり符号にしたがって埋められていく。左端のビットは符号によって、0(正の整数)または1(負の整数)になる。もし左端のビットが0ならば、0で埋められていく。もし左端のビットが1ならば、1で埋められていく。右端のビットは、捨てられていく。
オペランド2の範囲は、<<と同じだ。
符号無し右シフト演算子 >>>
シフト演算子「>>>」は整数のビットを符号無しで右にシフトする。>>>演算子のオペランド1のビットをオペランド2の数だけシフトする。
書き方の基本は簡単だ。
演算結果 = オペランド1 >>> オペランド2;
ビットが右にシフトされると、左端のビットはどうなるだろうか。符号無し、つまり符号に関係なく、左端のビットは0で埋められていく。右端のビットは、捨てられていく。
オペランド2の範囲は、<<と同じだ。
シフト演算子のサンプルプログラム
このサンプルプログラムは、前のセクションで例としてあげたビットの並びを4ビットシフトする演算をそのままプログラムに書いたものだ。実際のコードで書き方と演算結果を確かめよう。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
public class ShiftOperators { public static void main (String[] args) { int startBit0 = 0b0011_1111_1111_1111_1111_1111_1111_1101;//[1] int startBit1 = 0b1011_1111_1111_1111_1111_1111_1111_1101;//[2] int result;//[3] result = startBit1 << 4;//[4] System.out.println("[4] 0b10111111111111111111111111111101 << 4 = " + Integer.toBinaryString(result)); result = startBit1 >> 4;//[5] System.out.println("[6] 0b10111111111111111111111111111101 >> 4 = " + Integer.toBinaryString(result)); result = startBit0 >> 4;//[7] System.out.println("[8] 0b00111111111111111111111111111101 >> 4 = 000000" + Integer.toBinaryString(result)); result = startBit1 >>> 4;//[9] System.out.println("[10] 0b10111111111111111111111111111101 >>> 4 = 0000" + Integer.toBinaryString(result)); } } |
実行結果
1 2 3 4 |
[4] 0b10111111111111111111111111111101 << 4 = 11111111111111111111111111010000 [6] 0b10111111111111111111111111111101 >> 4 = 11111011111111111111111111111111 [8] 0b00111111111111111111111111111101 >> 4 = 00000011111111111111111111111111 [10] 0b10111111111111111111111111111101 >>> 4 = 00001011111111111111111111111111 |
サンプルプログラムの説明
それでは簡単にプログラムの解説をしてゆこう。
- [1] startBit0を宣言し、0b0011_1111_1111_1111_1111_1111_1111_1101を代入する。
- [2] startBit1を宣言し、0b1011_1111_1111_1111_1111_1111_1111_1101を代入する。
- [3] resultを宣言する。
- [4] resultにstartBit1 << 4を代入する。
- [5] resultを表示する。
- [6] resultにstartBit1 >> 4を代入する。
- [7] resultを表示する。
- [8] valueにstartBit0 >> 4を代入する。
- [9] resultを表示する。
- [10] valueにstartBit1 >>> 4を代入する。
- [11] resultを表示する。
まとめ
このページではJavaのシフト演算子についてまとめてきた。
すぐには使わないかもしれないが、ビット演算子と共になんとなくの全体像は把握しておくといいだろう。