默认情况下,struct alignment rules,16是正确的答案.每个字段都对齐以匹配其大小,因此您最终得到两个字节的短路,然后是六个字节的填充(到达下一个地址,对齐到八个字节的倍数),然后是八个字节.
您可以使用byte order prefix(其中任何一个禁用填充),但它们也会禁用机器本机大小(因此struct.calcsize(“= l”)将在所有系统上固定4个字节,并且struct.calcsize(“= hl”) )在所有系统上将是6个字节,而不是10个字节,即使在长度为8个字节的系统上也是如此).
如果要使用具有非默认填充规则的机器本机类型计算任意结构的结构大小,则需要转到ctypes模块,使用所需的_pack_设置定义ctypes.Structure子类,然后使用ctypes.sizeof检查大小,例如:
from ctypes import Structure, c_long, c_short, sizeof
class HL(Structure):
_pack_ = 1 # Disables padding for field alignment
# Defines (unnamed) fields, a short followed by long
_fields_ = [("", c_short),
("", c_long)]
print(sizeof(HL))
根据需要输出10.
如果需要,可以将其作为实用函数进行考虑(这是一个不处理所有结构格式代码的简化示例,但如果需要可以扩展):
from ctypes import *
FMT_TO_TYPE = dict(zip("cb?hHiIlLqQnNfd",
(c_char, c_byte, c_bool, c_short, c_ushort, c_int, c_uint,
c_long, c_ulong, c_longlong, c_ulonglong,
c_ssize_t, c_size_t, c_float, c_double)))
def calcsize(fmt, pack=None):
'''Compute size of a format string with arbitrary padding (defaults to native)'''
class _(Structure):
if packis not None:
_pack_ = pack
_fields_ = [("", FMT_TO_TYPE[c]) for c in fmt]
return sizeof(_)
一旦定义,它可以让你计算填充或未填充的大小,如下所示:
>>> calcsize("hl") # Defaults to native "natural" alignment padding
16
>>> calcsize("hl", 1) # pack=1 means no alignment padding between members
10