20

通过一些 Python 代码,我注意到十六进制值有许多不同的表示形式。例如,如果我选择这样的数字:

xx = '\x03\xff'

然后是以下命令(我用来将小端转换为大端的版本)

yy = hex(struct.unpack('>H', xx)[0])

将返回:

'0x3ff'

但是,这个命令

zz = xx.encode('hex')

将返回:

'03ff'

最后,只打印值将返回这个

'\x03\xff'

从外观上看,有三种不同类型的十六进制。

  1. '\xFF'
  2. '0xFF'
  3. 'FF'

有什么不同?

如果有人可以提出将小端数转换为大端数的更好方法,则加分。上面的方法对于yy大于两个字节的数字并不适用,我正在使用一些 16 字节长的十六进制字符串(包括不对应于 ascii/整数值的值)

4

2 回答 2

9

任何使用\x都是字符串转义码,恰好使用十六进制表示法;其他转义码包括\n换行符、\'文字引号等。python 字符串是一个字节序列,您可以使用这些字符指定 ASCII 可打印范围之外的文字值。当 Python 在解释器中回显一个字符串值,或者你打印repr()一个字符串调用的结果时,Python 将使用这种转义来表示任何不能打印为 ASCII 字符的字节:

>>> chr(65)
'A'
>>> chr(11)
'\x0b'

hex()函数返回一个非常具体的字符串表示,.encode('hex')不同之处在于前者包含0x前缀。还有两种方法可以产生这样的字符串表示;使用'%x'and'%X'字符串格式化程序,它们使用小写或大写字母表示。

>>> hex(11)
'0xb'
>>> '\x0b'.encode('hex')
'0b'
>>> '%x' % (11,)
'b'
>>> '%X' % (11,)
'B'

尽管这些都是字符串表示(一系列 ASCII 字符),并且与原始数据的关系与str(number)整数数据的关系相同;您已经更改了类型,并且离更改字节顺序的目标更远了。

将一条二进制信息从小端转换为大端需要您知道该信息的大小。如果你只有短整数,那么你需要每两个字节翻转一次,但如果你有普通(长)整数,那么每个值有 4 个字节,你需要每 4 个字节反转。

我认为使用struct模块是一种很好的方法,因为您必须指定值类型。以下将解释xx为 big-endian unsigned short int,然后将其打包回二进制表示为 little-endian unsigned short int:

>>> import struct
>>> xx = '\x03\xff'
>>> struct.pack('<H', *struct.unpack('>H', xx))
'\xff\x03'
于 2012-10-29T15:09:44.030 回答
2

'\xFF' 表示包含 ASCII 码为 255 的字符的字符串。

例如: print '\x41'给出 'A'(因为这是 ASCII 码 41 的字符)

并且xx.encode('hex')hex(struct.unpack('>H', xx)[0])给出字符串 xx 包含的 ASCII 代码的人类可读的十六进制表示。这意味着生成的字符串包含 a 和 f 或 0 和 9 之间的许多字符。

于 2012-10-29T15:00:42.273 回答