2

我正在使用一个外部库,它输出一个带有数据类型“>u2”(大端、无符号、2 字节/16 位)的 numpy 数组。就我而言,只有 10 位有效(输出来自实际输出little-endian的硬件设备)。例如:

65283是最大值,对应于bin(65283)=0b1111111100000011直接 python 输出,或者00001111111111如果它是 little-endian。

我想将0-65283库的范围输出映射到0-1023对 10 位硬件功能有意义的范围。我该怎么做呢?

我尝试了以下方法:

>>>import numpy as np

>>>arr=np.array([65283, 6528, 652, 65, 6], dtype=">u2")
>>>print arr/64  # same as arr/2**6 and arr >> 6
[1020  102   10    1    0]
>>>print arr.byteswap()
[ 1023 32793 35842 16640  1536]

但这并没有给出预期的结果。我发现该bin()函数以大端格式输出(在这个 numpy 数组的情况下),但省略了填充零。例如,65283 表示所有 16 位,但是bin(6528)=0b1100110000000(中间缺少 3 个零)。

为了解决这个问题(并返回一个 10 位的小端数),我可以得到 6528 的二进制形式,在中间添加 3 个零,然后进行字节交换。但是 1)这是超级乏味的(每个元素都完成)和 2)零填充不一致(例如 652 需要 6 个零)。

有没有内置的方法可以做到这一点?看起来struct模块(带pack和或unpack)可能会有所帮助,但现在对我来说是希腊语。任何帮助,将不胜感激!

编辑

相信我已经找到了罪魁祸首。我上面的示例(从 65238 的相机/库中获取实际值并假设半任意附加值,显然只是删除了最右边的数字)不会发生!例如,6528 需要在最低有效字节 ( 00011001**1**0000000) 中为 1,而这永远不会发生(只有 10 位有效)。

经过进一步检查,arr.byteswap()我的代码中的一个简单(arr具有合法值)可以工作。例如:

>>>arr=np.array([12288, 13312, 12800, 12032, 13312, 13824, 65283, 0, 7936], dtype=">u2")
>>>arr.byteswap()
array([  48,   52,   50,   47,   52,   54, 1023,    0,   31], dtype=uint16)

我从来没有在我的代码中真正尝试过,只是在这个虚构的例子中。对困惑感到抱歉。但希望它可以帮助其他人解决这个问题(特别是如果你使用 Basler 相机!),我猜这结果是微不足道的......

4

1 回答 1

0
import struct
struct.pack('<H',val)

或者,更好的是:

>>> arr.byteswap().newbyteorder()
array([65283,  6528,   652,    65,     6], dtype=uint16)
>>> arr.byteswap().newbyteorder().tostring()
'\x03\xff\x80\x19\x8c\x02A\x00\x06\x00'

文档

于 2012-05-09T21:48:24.533 回答