リトルエンディアンとビッグエンディアン
作成日:2019/08/12
仕事でバイナリデータの読み書きをする際に自作ツールとメーカーツールで結果が異なったため、その原因調査の一貫として勉強したことの備忘。
バイトオーダ
多バイトのデータをどういう順番でメモリに格納するか。プロセッサによって異なる。Intelはリトルエンディアン。JVMはビッグエンディアン。
ネットワークにおいても多バイトデータをどう通信するか、バイトオーダを決める必要がある。TCP/IPはビッグエンディアン。
リトルエンディアン
下位ビットを低位のアドレスに格納する。順序が逆になる。
バイト列: 0x0123456789ABCDEF
メモリ配置: [EF, CD, AB, 89, 67, 45, 34, 01]
キャストする場合、下位のnバイトを読めばいいので効率がいい。上のバイト列(8バイト)を4バイトにキャストする場合、メモリの0番地〜3番地を読めばよい。
ビッグエンディアン
上位ビットを低位のアドレスに格納する。
バイト列: 0x0123456789ABCDEF
メモリ配置: [01, 23, 45, 67, 89, AB, CD, EF]
キャストする場合上位のnバイトを読むためにオフセットが必要になる。
実験
C
code: (csharp=)
int data = 0x0123ABCD;
byte[] byteArray = BitConverter.GetBytes(data);
foreach(byte b in byteArray)
Console.Write($"{b:X2} ");
code:_
出力結果
CD AB 23 01
リトルエンディアンのため元のデータと逆順で出力される。
Java
code: (java=)
int data = 0x0123ABCD;
byte[] byteArray = ByteBuffer.allocate(4).putInt(data).array();
for (byte b : byteArray) {
System.out.printf("%02X ", b);
code:_
出力結果
01 23 AB CD
ビッグエンディアンのため元のデータと同じ順序で出力される。
参考