Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does mixing types in Python struct.pack uses more space than needed?

Tags:

python

pack

I have just tried using struct.pack in Python for the first time, and I don't understand its behaviour when I am mixing types

When I am trying to pack a single char and nothing else, it works as expected, i.e.

struct.pack("b",1)

gives '\x01'. But as soon as I try to mix in data of a different type, the char is padded to be as long as this type, e.g.

struct.pack("bi",1,1)

gives '\x01\x00\x00\x00\x01\x00\x00\x00'.

Is this standard behaviour, and why? Is there a way around it?

Edit

More simply put:

>>> struct.calcsize("b")
1
>>> struct.calcsize("i")
4
>>> struct.calcsize("bi")
8
like image 910
scozy Avatar asked Jan 24 '14 12:01

scozy


2 Answers

struct.pack is usually used to access memory structures, not files. In memory, accessing data which occupies several bytes at an odd/unaligned address can cause exceptions or performance loss.

That's why compilers align the data (usually on a 4 or 8 byte boundary) and the struct module in Python does the same.

To disable this, you can use the first character of the format string to set the byte order and alignment. In your case, try struct.pack("=bi",1,1)

If you don't specify anything, then an implicit @ which means "native byte order, size and alignment". See the documentation for other options.

like image 107
Aaron Digulla Avatar answered Oct 23 '22 13:10

Aaron Digulla


Yes, it is.

By default, C types are represented in the machine’s native format and byte order, and properly aligned by skipping pad bytes if necessary (according to the rules used by the C compiler).

If you don't want alignment, just specify a byte order by starting your format string with '=', '<', or '>' (same as '!').

like image 43
Dan Getz Avatar answered Oct 23 '22 14:10

Dan Getz