2017-09-13 4 views
0

構造体をバイナリファイルからアンパックしようとしていますが、最初の4バイトは整数(値64)で、次の3 * 8バイトは3倍です。 Python構造体のアンパック整数の後にdoubleが続く

print(struct.unpack("i", fileContent[0:4])) 

と、これは正しく番号64を印刷しますしかし、私はまた、次のダブルを読みたい:その後、私は試す

with open('data', mode='rb') as file: 
    fileContent = file.read() 

:私はこのような含むFileContentと呼ばれるベクトルにデータを格納しています私は(12バイトの総数を得、整数は4バイトであるべきであり、ダブル8でなければならないので)

print(struct.unpack("id", fileContent[0:12])) 

に上記のステートメントを変更します。私はダブルのみと使用を読みしようとした場合しかし、私は、また

struct.error: unpack requires a bytes object of length 16

というエラーが出ます:

print(struct.unpack("d", fileContent[4:12]) 

私は、二重の正しい値を得ることはありません!上記スライスを[8:16]に変更すると、正しい値が得られます。誰かがこれを説明できますか?ファイルの最初の4バイトは整数で、次の8バイトは2倍でなければなりません。 read()は何らかの理由で整数をゼロで埋めますか、何が起こっていますか?

+0

あなたの入力構造はおそらく埋め込まれているので、 'double'は8バイトに整列します。 –

+0

私はターミナルでバイナリダンプを作成しました。入力ファイル 'data'はパディングされていません(リトルエンディアンマシンのアカウント、最初の4バイトは01000000 00000000 00000000 00000000です)。彼らはフロートを表すと思う。自動的にデータを埋め込むread()関数がありますか? – JezuzStardust

答えて

0

unpack()は自動的に埋め込みを行います。したがってunpack('id', …)は整数を8バイトに埋め込みます。そのため、「struct.error:unpackには長さ16のバイトオブジェクトが必要です」というエラーが発生しています。

それは簡単にこのように見ることができます。

>>> pack('id', 42, 42) 
b'*\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\[email protected]' 

しかし、修正プログラムは、ファイルのエンディアンを知っているとして、あなたはそれを指定する必要があり、それをspecifingことで、パディングが無効になり、簡単です。

>>> unpadded = pack('>id', 42, 42) 
>>> len(unpadded) 
12 
>>> unpack('>id', unpadded) 
(42, 42.0)