Python,如何解码二进制编码的十进制(BCD)

Whi*_*rse 9 python binary struct decode bcd

二进制字段的描述是:

呼叫者号码,用压缩的BCD码表示,剩余比特用"0xF"填充

我试图用struct格式打印,'16c'然后得到:('3', '\x00', '\x02', '\x05', '\x15', '\x13', 'G', 'O', '\xff', '\xff', '\xff', '\xff', '\xff', '\xff', '\xff', '\xff')如果我使用'16b'我得到(51, 0, 2, 5, 21, 19, 71, 79, -1, -1, -1, -1, -1, -1, -1, -1).这是不正确的,我应该得到电话号码,上面的数字是无效的.

print struct.unpack_from('>16b', str(data.read()),offset=46)
Run Code Online (Sandbox Code Playgroud)

上面的代码不起作用,我得到无效的数字.我应该以什么格式解压缩16字节字段以及如何转换BCD代码?

Mar*_*ers 17

BCD码每个数字使用4位,通常只编码0到9位数.因此序列中的每个字节包含2个数字,每4位信息1个.

以下方法使用生成器来生成这些数字; 我假设0xF值意味着没有更多数字要遵循:

def bcdDigits(chars):
    for char in chars:
        char = ord(char)
        for val in (char >> 4, char & 0xF):
            if val == 0xF:
                return
            yield val
Run Code Online (Sandbox Code Playgroud)

在这里,我使用右移运算符将最左边的4位向右移动,使用按位AND选择最右边的4位.

示范:

>>> characters = ('3', '\x00', '\x02', '\x05', '\x15', '\x13', 'G', 'O', '\xff', '\xff', '\xff', '\xff', '\xff', '\xff', '\xff', '\xff')
>>> list(bcdDigits(characters))
[3, 3, 0, 0, 0, 2, 0, 5, 1, 5, 1, 3, 4, 7, 4]
Run Code Online (Sandbox Code Playgroud)

该方法适用于c输出; ord如果直接传递整数,则可以跳过方法中的调用(但使用B无符号变量).或者,您可以直接从文件中读取这16个字节,并直接将此函数应用于这些字节而不使用struct.