HOWTO · Python

如何在 Python 中创建 BitArray

学习如何使用这个综合指南在 Python 中创建一个位数组。探索使用内置数组模块、bitarray 库和 numpy 的方法。发现清晰的代码示例和解释,以提升您的编程技能。适合初学者和经验丰富的开发人员!

本页内容

位数组是由单个二进制值组成的序列,每个值只能是 0 或 1。在 Python 中,“位数组”可能指不同的存储模型:打包序列会将多个位一起存储;字节数组为每个元素存储一个数值字节;布尔数组则存储真值。选择时应根据要表示的数据和所需操作来决定;这些类型都能表示类似二进制的值,但并不能因此互换。

Python 中位数组的含义

这种区别会影响实际使用。如果需要真正的位序列,请使用第三方 bitarray 套件。如果需要数值字节元素,且其值恰好为 0 或 1,可以用标准库中的 array.array 表示;但每个元素仍是一个字节大小的数值。如果要对真值和假值进行面向数组的计算,NumPy 的布尔数据类型可能适用。不要把 array.array 或 NumPy 布尔数组称为打包位。

选择合适的表示方式

表示方式 每个元素的含义 设置方式 适用场景
bitarray 一个位 安装第三方套件 对位序列进行位索引和位运算
array.array('B') 一个无符号字节,取值范围为 0 到 255 Python 标准库 数值字节;表示二进制标志时只使用 0 和 1
NumPy 布尔数组 一个布尔值 安装 NumPy 处理真值或假值的数组操作

没有一种方案适用于所有情况。如果数据本身是位序列,可以先考虑 bitarray。如果值是字节或小整数,可以选择 array.array。如果后续计算需要 NumPy 数组,则可选择 NumPy。下面的示例会说明每种方式中元素的含义。

使用 bitarray 创建打包位

bitarray 不属于 Python 标准库。请在项目使用的环境中通过 python -m pip install bitarray 安装。从字符串构造位序列可以直观地看出位的顺序。该套件也支持位序列操作;对于取决于具体操作或序列化格式的细节,请查阅已安装套件的文档。

本节中的代码以及显示的标签或输出仍为英文。

try:
    from bitarray import bitarray
except ImportError:
    print("Install bitarray with: python -m pip install bitarray")
else:
    bits = bitarray('11010101')
    bits[0] = 0
    print(bits.to01())

此示例从字符串中的字符构造八个打包位,并通过索引修改第一位。提供的运行案例没有显示此 bitarray 操作成功运行,因此这里不报告输出。如果尚未安装可选套件,导入保护代码会让示例正常退出,并显示英文安装提示;代码中的提示保持英文。使用演示的操作前,请先安装该套件。

使用 array.array 表示位

Python 标准库包含 array 模块。其类型代码 'B' 表示无符号字节,因此取值范围为 0 到 255。如果这些值用来表示二进制标志,应将它们限制为 0 和 1;该类型本身不会强制这一限制。每个元素仍是一个数值字节,而不是可以单独寻址的打包位。

运行下面这个独立示例:

本节中的代码以及显示的标签或输出仍为英文。

import array

values = array.array('B', [1, 1, 0, 1])
values[2] = 1
print(list(values))
[1, 1, 1, 1]

代码创建四个字节元素,修改第三个元素,并将它们作为普通 Python 列表打印。这是一个只使用标准库的示例,不需要其他文件或套件。

使用 NumPy 布尔数组

NumPy 提供布尔数据类型,通常写作 np.bool_。如果尚未安装,请通过 python -m pip install numpy 安装 NumPy。当后续步骤要使用 NumPy 数组操作时,布尔数组很有用;但其值是 True 和 False,并不是打包位表示。

本节中的代码以及显示的标签或输出仍为英文。

try:
    import numpy as np
except ImportError:
    print("Install NumPy with: python -m pip install numpy")
else:
    flags = np.array([1, 1, 0, 1], dtype=np.bool_)
    flags[2] = True
    print(flags.tolist())
[True, True, True, True]

该示例将数值输入转换为布尔值,并修改其中一个位置。如果环境中没有 NumPy,导入保护代码会显示英文安装提示,并让代码片段正常退出;提示在代码中保持英文。

转换、操作和存储位序列

需要访问或修改单个位时,bitarray 可以直接表示位序列;索引和赋值操作针对的是位的位置。对于 array.array('B'),索引访问的是字节元素,因此也可以表示 0 和 1 以外的值。对于 NumPy,索引访问的是布尔元素。应根据表示方式选择相应操作,不要假定这三种方式具有相同的存储或转换行为。

将位转换为整数时,必须确定哪一位是最高有效位,以及该值包含多少位。这些选择会影响转换结果,尤其是在需要保留前导零位时。由于缺少经过验证的 API 行为,本指南不指定特定套件的整数转换调用。同样,存储或交换位序列时,需要约定编码方式和位顺序;不要假定打印出来的表示形式是可移植的序列化格式。请查阅所选套件文档中的转换或序列化 API,并在数据格式中记录位宽和顺序规则。

常见问题

什么是位数组? 位数组是一串以单个二进制值为元素的序列。打包位数组将位作为位存储;字节数组或布尔数组也可以表示二进制值,但它们的元素模型不同。

可以修改单个位吗? 可以。bitarray 支持按位的位置进行索引和赋值。示例还展示了如何修改一个字节数组元素或一个布尔数组元素;这些位置分别指向各自类型的元素,而不是打包位。

bitarray 属于 Python 吗? 不属于。它是需要单独安装的第三方套件。array.array 属于标准库;NumPy 也是外部套件。

应该选择哪种表示方式? 位序列使用 bitarray,字节值使用 array.array('B');如果工作需要 NumPy 的数组模型,则使用 NumPy 布尔数组。

可以将位数组转换为整数吗? 转换前需要明确位顺序和位宽。请查阅所选套件文档中的 API,并将这些规则与数值一同保留;本文不假定存在未经验证的转换方法。