我想將一個10位整數和一個54位整數打包爲一個64位結構。但是這個代碼最終使用了128位。Python中的壓縮位字段
from ctypes import *
class ABC(Structure):
_fields_ = [("a", c_int, 10), ("b", c_uint64, 54)]
print(sizeof(ABC) * 8) # 128
我想將一個10位整數和一個54位整數打包爲一個64位結構。但是這個代碼最終使用了128位。Python中的壓縮位字段
from ctypes import *
class ABC(Structure):
_fields_ = [("a", c_int, 10), ("b", c_uint64, 54)]
print(sizeof(ABC) * 8) # 128
無論出於何種原因,當你混合不同寬度的對象到相同的字節不做到位了包裝正確。像這樣的東西似乎適用於我:
class ABC(Structure):
_pack_ = 1
_fields_ = [("a",c_int64,10),("b",c_uint64,54)]
'_pack_'屬性究竟做了什麼以及它的有效值是什麼? – mcu
http://stackoverflow.com/questions/14771150/python-ctypes-pragma-pack-for-byte-aligned-read - 本質上它模擬C的'pragma pack',但由於你的結構是字節對齊到標準寬度已經可能沒有影響 –
至於有效的值,https://docs.python.org/2/library/ctypes.html#ctypes.Structure._pack_和其他評論,同時搜索表明,它會採取小正面權力2 –
考慮int_10
和int_54
與所需位數的整數:
>>> def pack(int_10, int_54):
... return (int_10 & 0x3FF) | (int_54 & 0x3FFFFFFFFFFFFF) << 10
>>> bin(pack(1, 1))
'0b10000000001'
>>> bin(pack(1, 2 ** 54 - 1))
'0b1111111111111111111111111111111111111111111111111111110000000001'
>>> bin(pack(2 ** 10, 2 ** 54))
'0b0'
然後,您可以使用struct.pack
得到一個字節的字符串填料上的整數。
>>> import struct
>>> struct.pack('Q', pack(2 ** 10 - 1, 2 ** 54 - 1))
'\xff\xff\xff\xff\xff\xff\xff\xff'
這可以用於壓縮存儲等數據。但它不會讓我輕易操縱位域,如:'x = ABC(10,20); x.a = -15; x.b = 50'如果存在,我真的在尋找Python的內置功能。 – mcu
你認爲只有無符號整數? –
不,已簽名且未簽名。但是如果你只有一個沒有簽名的解決方案,我希望看到它。 – mcu