如何从np.packbits结果解包比特?解决异或后维度不符问题
问题:使用np.packbits执行异或后无法得到预期维度的结果
我不熟悉np.packbits,希望借助它执行大规模异或(XOR)操作。以下是我的示例代码:
import numpy as np # Example arrays u_values = np.array([[True, True, True, True, True, True, False, True, True, True], [True, True, True, True, True, True, True, False, False, True], [True, True, True, True, False, True, False, True, True, True], [True, True, True, True, False, True, True, False, False, True], [True, True, True, True, True, False, False, False, False, True], [True, True, True, False, False, False, False, False, False, True], [True, False, False, False, False, False, False, False, False, True], [True, True, False, True, False, True, False, True, True, True]]) v_values = np.array([[True, True, True, True, True, True, False, True, True, True], [True, False, True, False, True, True, True, False, False, True], [True, True, True, True, False, True, False, True, True, True], [True, False, True, True, False, False, True, False, False, True], [True, True, False, True, True, False, False, False, False, True], [True, True, True, False, False, True, False, False, False, True]])
我尝试使用以下代码:
u_values_packed = np.packbits(u_values, axis=1) v_values_packed = np.packbits(v_values, axis=1) result_packed = u_values_packed[:, None, :] ^ v_values_packed[None, :, :] result_packed = result_packed.reshape((-1, result_packed.shape[2])) result_unpacked = np.unpackbits(result_packed, axis=1) print(result_unpacked.shape) #(48,16)
得到的输出形状为(48,16),而非预期的(48,10)。如何实现u_values每行与v_values每行的异或,得到维度为(48,10)的结果?
预期输出如下:
[[False False False False False False False False False False] [False True False True False False True True True False] [False False False False True False False False False False] [False True False False True True True True True False] [False False True False False True False True True False] [False False False True True False False True True False] [False False False False False False True True True False] [False True False True False False False False False False] [False False False False True False True True True False] [False True False False True True False False False False] [False False True False False True True False False False] [False False False True True False True False False False] [False False False False True False False False False False] [False True False True True False True True True False] [False False False False False False False False False False] [False True False False False True True True True False] [False False True False True True False True True False] [False False False True False False False True True False] [False False False False True False True True True False] [False True False True True False False False False False] [False False False False False False True True True False] [False True False False False True False False False False] [False False True False True True True False False False] [False False False True False False True False False False] [False False False False False True False True True False] [False True False True False True True False False False] [False False False False True True False True True False] [False True False False True False True False False False] [False False True False False False False False False False] [False False False True True True False False False False] [False False False True True True False True True False] [False True False False True True True False False False] [False False False True False True False True True False] [False True False True False False True False False False] [False False True True True False False False False False] [False False False False False True False False False False] [False True True True True True False True True False] [False False True False True True True False False False] [False True True True False True False True True False] [False False True True False False True False False False] [False True False True True False False False False False] [False True True False False True False False False False] [False False True False True False False False False False] [False True True True True False True True True False] [False False True False False False False False False False] [False True True False False True True True True False] [False False False False True True False True True False] [False False True True False False False True True False]]
解决方案
问题出在np.packbits的对齐机制上:它会将输入的布尔数组按8位为一组进行打包,不足8位的部分会补0填充。你的每行有10个元素,打包后会占用2个字节(16位),所以unpackbits后会还原出16位,导致结果多出6个无效的补位。
要得到预期的(48,10)形状,只需要在unpackbits后截断多余的列,保留前10个元素即可。修改后的代码如下:
import numpy as np u_values = np.array([[True, True, True, True, True, True, False, True, True, True], [True, True, True, True, True, True, True, False, False, True], [True, True, True, True, False, True, False, True, True, True], [True, True, True, True, False, True, True, False, False, True], [True, True, True, True, True, False, False, False, False, True], [True, True, True, False, False, False, False, False, False, True], [True, False, False, False, False, False, False, False, False, True], [True, True, False, True, False, True, False, True, True, True]]) v_values = np.array([[True, True, True, True, True, True, False, True, True, True], [True, False, True, False, True, True, True, False, False, True], [True, True, True, True, False, True, False, True, True, True], [True, False, True, True, False, False, True, False, False, True], [True, True, False, True, True, False, False, False, False, True], [True, True, True, False, False, True, False, False, False, True]]) # 打包数组 u_packed = np.packbits(u_values, axis=1) v_packed = np.packbits(v_values, axis=1) # 执行广播异或:u的每行和v的每行逐一异或 result_packed = u_packed[:, None, :] ^ v_packed[None, :, :] # 展平为二维数组 result_packed_flat = result_packed.reshape(-1, result_packed.shape[2]) # 解包后截断到原长度10 result_unpacked = np.unpackbits(result_packed_flat, axis=1)[:, :10] print(result_unpacked.shape) # 输出 (48, 10) # 验证是否与预期一致 # print(np.array_equal(result_unpacked, 你的预期输出数组)) # 替换后可验证为True
关键说明:
np.packbits打包时,会自动将每行的长度向上取整到8的倍数(10→16),所以解包后需要手动截断回原长度。- 这种打包异或的方式在处理大规模布尔数组时,比直接对布尔数组做广播异或更节省内存,适合大数据场景。
内容的提问来源于stack exchange,提问作者Erwin
相关产品推荐
相关产品推荐

