More than 3 years have passed since last update.


エンディアンとは

エンディアンってのバイナリファイルにおけるバイトオーダーのこと。

例えばあるデータが2バイトで保存されているとする。

00000001 00000000

この時、どっちのバイトが0~255の値を示す(すなわち小さい位から1,2,4,8...の位である)。

もう一方は256~65535の値を表す(すなわち小さい位から256,512,1024...の位である)。

ビッグエンディアンだと、はじめのバイトのほうが大きい数字を表す。

上の例では1バイト目が256~32768の位であり、2バイト目が1~128のくらいであるってこと。

これは普段私達が見ている数字と同じ感じ。

リトルエンディアンだと逆にはじめのバイトのほうが小さいくらいを示す。

なお、バイト内では最後の数字が一番小さい位であるというのは変わらない(?)(←よくわからないので分かる人コメントください)

現代では多くのシステムがIntelチップを採用したためにWinもMacもリトルエンディアンになったが、巷にはビッグエンディアンのデータがゴロゴロ転がっている。

リトルエンディアンのつもりでビッグエンディアンのデータを触ると結果がおかしくなり痛い目にあうので注意が必要。

このページではエンディアンを切り替える方法を(僕がよく使う言語に関して)まとめました。


Fortran

Fortranではコンパイル時にもともとエンディアンを決めちゃう方法と、プログラム中でファイルを読み込む際に切り替える方法がある。


コンパイル時に決める

これは超簡単。

gfortranを使っているなら以下のようにコンパイルすればおk。

ただし、プログラム中の全部がビッグエンディアンになるので注意がいる。

gfortran -fconvert=big-endian -o test test.f90


環境変数で装置番号ごとに変える

export F_UFMTENDIAN="little;big 87"

こうすると基本はリトルエンディアン装置番号87だけビッグエンディアンってなる。

もちろんbigsmallをひっくり返しても可。

;からあとは省略しても可。


Python

ファイルを読み込むときに決めちゃうのが簡単。

例えば画像を作るのにデータを読み込むとする。まず、配列に開いたファイルのデータを入れる。

imagearr=np.fromfile(rfile,'<h',NROWS*NCOLS*1)

imagearrが画像を作る元のデータを入れておく配列。

npはnumpy。

rfileはファイルのディレクトリ。

NROWS*NCOLS*1は行数×列数を示す。

ここで<hってのがエンディアンと読みこむ変数の種類を示す。

はじめの<はリトルエンディアンを示し。

hはint16を示す。

以下にその他の例を示す。

文字
バイトオーダ
サイズ
アラインメント

@
ネイティブ
native
native

=
ネイティブ
standard
none

<
リトルエンディアン
standard
none

>
ビッグエンディアン
standard
none

!
ネットワーク (= ビッグエンディアン)
standard
none

フォーマット
C での型
Python 型
標準のサイズ
備考

x
pad byte
no value
 
 

c
char
長さ 1 の文字列
1
 

b
signed char
整数型 (integer)
1
(3)

B
unsigned char
整数型
1
(3)

?
_Bool
真偽値型(bool)
1
(1)

h
short
整数型
2
(3)

H
unsigned short
整数型
2
(3)

i
int
整数型
4
(3)

I
unsigned int
整数型
4
(3)

l
long
整数型
4
(3)

L
unsigned long
整数型
4
(3)

q
long long
整数型
8
(2), (3)

Q
unsigned long
long
整数型
8
(2), (3)

f
float
浮動小数点型
4
(4)

d
double
浮動小数点型
8
(4)

s
char[]
文字列
 
 

p
char[]
文字列
 
 

P
void *
整数型
 
(5), (3)

ソース:http://docs.python.jp/2/library/struct.html