Python是否具有位域类型?

时间:2020-03-06 14:49:01  来源:igfitidea点击:

我需要布尔数组的紧凑表示形式,Python是否具有内置的位域类型,还是需要找到其他解决方案?

解决方案

NumPy有一个数组接口模块,可用于创建位域。

我们可能需要使用BitVector软件包。它不是内置在我的python安装中,但很容易在python站点上找到。

当前版本的https://pypi.python.org/pypi/BitVector。

当我最近有类似需求时,Bitarray是我找到的最佳答案。它是C的扩展(比纯Python的BitVector快得多),并将其数据存储在实际的位域中(因此,内存效率是numpy布尔数组的八倍,后者似乎每个元素使用一个字节。)

如果位字段很短,则可以使用struct模块。否则,我建议在数组模块周围使用某种包装。

另外,ctypes模块确实包含位域,但我自己从未使用过它。买者自负。

我使用二进制按位运算符!,&,|,^,>>和<<。它们工作得非常好,可以直接在底层C中实现,而底层C通常直接在底层硬件上。

将每个值表示为两个的幂:

testA = 2**0
testB = 2**1
testC = 2**3

然后将值设置为true:

table = table | testB

要将值设置为false,请执行以下操作:

table = table & (~testC)

要测试一个值:

bitfield_length = 0xff
if ((table & testB & bitfield_length) != 0):
    print "Field B set"

如果这对我们没有意义,请更深入地了解十六进制表示形式。基本上,这也是在嵌入式C应用程序中跟踪布尔标志的方式(如果内存有限)。

我们应该看一下bitstring模块,该模块最近已达到2.0版。
二进制数据紧凑地存储为字节数组,可以轻松创建,修改和分析。

我们可以从二进制,八进制,十六进制,整数(大端或者小端),字符串,字节,浮点数,文件等创建" BitString"对象。

a = BitString('0xed44')
b = BitString('0b11010010')
c = BitString(int=100, length=14)
d = BitString('uintle:16=55, 0b110, 0o34')
e = BitString(bytes='hello')
f = pack('<2H, bin:3', 5, 17, '001')

然后,我们可以使用简单的功能或者切片符号来分析和修改它们,而无需担心位掩码等。

a.prepend('0b110')
if '0b11' in b:
    c.reverse()
g = a.join([b, d, e])
g.replace('0b101', '0x3400ee1')
if g[14]:
    del g[14:17]
else:
    g[55:58] = 'uint:11=33, int:9=-1'

还有一个位定位的概念,因此如果对我们有用,我们可以将其视为文件或者流。属性用于对位数据进行不同的解释。

w = g.read(10).uint
x, y, z = g.readlist('int:4, int:4, hex:32')
if g.peek(8) == '0x00':
    g.pos += 10

此外,还支持标准的按位二进制运算符,打包,解压缩,字节序等。最新版本适用于Python 2.7和3.x,尽管它是纯Python,但在内存和速度方面都进行了合理的优化。

如果要使用整数(或者长整数)表示为布尔数组(或者整数集),请查看http://sourceforge.net/projects/pybitop/files/

它提供将位字段插入/提取到长整型中的功能;查找最高有效或者最低有效的" 1"位;计算所有1;位反转诸如此类的东西在纯python中都是可能的,但在C语言中则要快得多。