Python处理16进制byte数据:从字符串转换到文件存储的完整指南

方予
方予
发布时间:2026-10-16| 3人浏览过
原创

本文详解Python中处理16进制byte数据的多种方法。针对byte转str再存文件导致的转义字符混乱问题,提供了手动解析\x格式的生成器方案及更简单的数字列表存储法。同时梳理了hex()与int()函数的进制转换语法,帮助开发者高效处理网络编程中的二进制数据持久化。

如何读取16进制byte数据

在进行网络编程时,常需处理非标准字符串的byte数据,例如类似b'\x00\xff\xfe\x01'的格式。这类数据属于16进制编码的byte类型,直接转为字符串虽无报错,但若再次转回bytes类型,往往会出现多余的双斜杠等异常现象,令人困扰。

a = b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x19\x39\xd9\x9d\xfdABCDabcd'
b = str(a)
 
print(b)
>>> b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x199\xd9\x9d\xfdABCDabcd'
 
print(bytes(b,'utf8'))
>>> b"b'\\x00\\xef\\xa2\\xa0\\xb3\\x8b\\x9d\\x1e\\xf8\\x98\\x199\\xd9\\x9d\\xfdABCDabcd'"

若尝试将此类数据写入文件后再读取,结果依然不理想。原因在于写入时将其作为普通字符串处理,导致原始的二进制结构丢失,读取时无法还原。

# 写入data.txt
a = b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x19\x39\xd9\x9d\xfdABCDabcd'
with open('data.txt','w') as p:
    p.write(str(a))
 
# 读取data.txt
with open('data.txt','r') as p:
    line = p.readline()
 
print(line, type(line) == str)
>>> b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x199\xd9\x9d\xfdABCDabcd\\' True
 
print(bytes(line,'utf8'))
>>> b"b'\\x00\\xef\\xa2\\xa0\\xb3\\x8b\\x9d\\x1e\\xf8\\x98\\x199\\xd9\\x9d\\xfdABCDabcd\\\\'"

分析ASCII码可知,问题核心在于\x字符被解析器误读为反斜杠与字母x的组合,从而以字符串形式存储,占用两个字节,破坏了原有的单字节表示。

鉴于\xnn格式本质应视为ASCII码处理,可编写特定的转义逻辑进行读取解析。

def readbytetxt(filename):
    dic = {
    '0': 0,    '1': 1,    '2': 2,
    '3': 3,    '4': 4,    '5': 5,
    '6': 6,    '7': 7,    '8': 8,
    '9': 9,    'a': 10,   'b': 11,
    'c': 12,   'd': 13,   'e': 14,
    'f': 15,
    }
    with open(filename,'r') as p:
        line = p.readline()
        while line:
            if line[-1] == '\n':
                line = line[:-1]
            i = 2
            L = b''
            while i+1 < len(line):
                if line[i:i+2] == '\\x' and (line[i+2] in dic.keys()) and (line[i+3] in dic.keys()):
                    L += bytes([dic[line[i+2]]*16+dic[line[i+3]]])
                    i += 4
                else:
                    L += bytes(line[i],'utf8')
                    i += 1
            return L
            line = p.readline()
 
print(readbytetxt('data.txt'))
>>> b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x19\x39\xd9\x9d\xfdABCDabcd'

通过遍历字符串,识别\x标记,将后续两位16进制数转换为十进制整数,再解码为bytes对象,即可恢复常见的十六进制格式数据。

此外,还需处理其他转义字符如\\、\n等,否则仍会出现识别错误。改进后的函数支持多种常见转义字符,并采用生成器模式输出,提高了灵活性。

def readbytetxt2(filename):
    dic = {
    '0': 0,    '1': 1,    '2': 2,
    '3': 3,    '4': 4,    '5': 5,
    '6': 6,    '7': 7,    '8': 8,
    '9': 9,    'a': 10,   'b': 11,
    'c': 12,   'd': 13,   'e': 14,
    'f': 15,
    }
    dic2 = {
    'a': '\a',     'b': '\b', 
    'f': '\f',     'n': '\n', 
    'r': '\r',     'v': '\v', 
    '\'': '\'',    '\"': '', 
    '\\': '\\', 
    }
    with open(filename,'r') as p:
        line = p.readline()
        while line:
            if line[-1] == '\n':
                line = line[:-1]
            i = 2
            L = b''
            while i+1 < len(line):
                if line[i:i+2] == '\\x' and (line[i+2] in dic.keys()) and (line[i+3] in dic.keys()):
                    L += bytes([dic[line[i+2]]*16+dic[line[i+3]]])
                    i += 4
                elif line[i] == '\\' and line[i+1] in dic2.keys():
                    L += bytes(dic2[line[i+1]],'utf8')
                    i += 2
                elif line[i:i+4] == '\\000':
                    L += bytes('\000','utf8')
                    i += 2
                else:
                    L += bytes(line[i],'utf8')
                    i += 1
            yield L
            line = p.readline()
 
a = b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x19\x39\xd9\x9d\xfdthe first line\n\r\a\b\t\\\f\'\"\v\b\n\000'
b = b'\xa0\xdf\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x19\x39\xd9\x9d\xfdthe second line\nn'
c = b'\xe0\xaf\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x19\x39\xd9\x9d\xfdthe third line\\'
with open('data.txt','w') as p:
    p.write(str(a)+'\n')
    p.write(str(b)+'\n')
    p.write(str(c))
 
line = readbytetxt2('data.txt')
 
print([a for a in line])
>>> [b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x199\xd9\x9d\xfdthe first line\n\r\x07\x08\\t\\\x0c\'"\x0b\x08\n\x00', b'\xa0\xdf\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x199\xd9\x9d\xfdthe second line\nn', b'\xe0\xaf\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x199\xd9\x9d\xfdthe third line\\']

经过上述优化,大部分编码形式的读取问题得以解决。

然而,还存在一种更简便的处理思路。既然根本问题在于字符串格式中复杂的转义规则难以理清,而byte本身即为16进制数字表示,那么只需存储数字即可。因此,可直接将byte数据转换为数字列表进行存储。

L = []
a = b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x19\x39\xd9\x9d\xfdthe first line\n\r\a\b\t\\\f\'\"\v\b\n\000'
print(a)
for each in a:
    L.append(int(each))
with open('data.txt','w') as p:
    p.write(str(L))
print(L)
>>> [0, 239, 162, 160, 179, 139, 157, 30, 248, 152, 25, 57, 217, 157, 253, 116, 104, 101, 32, 102, 105, 114, 115, 116, 32, 108, 105, 110, 101, 10, 13, 7, 8, 9, 92, 12, 39, 34, 11, 8, 10, 0]
 
 
with open('data.txt','r') as p:
    line = p.readline()
print(b''.join([bytes([int(i)]) for i in line[1:-1].split(',')]))
>>> b'\x00\xef\xa2\xa0\xb3\x8b\x9d\x1e\xf8\x98\x199\xd9\x9d\xfdthe first line\n\r\x07\x08\t\\\x0c\'"\x0b\x08\n\x00'

读取时,利用split方法分割数字列表,再逐个转换回bytes。这种方式避免了转义字符带来的歧义,确保数字对应什么byte就还原为什么byte,简单可靠。

Python的十六进制数

转换关系

十进制整数转十六进制整数使用hex()函数;十六进制整数转十进制整数使用int()函数。

同理,十进制整数转二进制整数使用bin()函数;十进制整数转八进制整数使用oct()函数。

hex() 函数

描述:hex() 函数用于将10进制整数转换成16进制,以字符串形式表示。

语法:

  • hex(x)

参数说明:x – 10进制整数

返回值:返回16进制数,以字符串形式表示。

int() 函数

描述:int() 函数用于将一个字符串或数字转换为整型。

语法:

  • class int(x, base=10)

参数说明:x – 字符串或数字。base – 进制数,默认十进制。

返回值:返回整型数据。

运算

对于十六进制整数,在进行运算前先转换成十进制整数,再对其进行运算,之后将运算结果转换回十六进制数。

以上为个人经验,希望能给大家一个参考,也希望大家多多支持本站。

相关标签:

免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。

Python 相关产品和应用

全部下载
Selenium

Selenium

4.51.0 · Windows

用于浏览器自动化和 Web 测试的 Python 工具。

scikit-learn

scikit-learn

1.9.1 · Windows

常用 Python 机器学习算法与模型评估工具库。

Black

Black

26.10.1 · Windows

强调一致性的 Python 自动代码格式化工具。

Ruff

Ruff

0.17.1 · macOS

由 Rust 编写的高速 Python 代码检查和格式化工具。

pytest

pytest

9.1.1 · Windows

简洁而强大的 Python 自动化测试框架。

FastAPI

FastAPI

0.146.0 · Windows

高性能 Python API 框架,支持类型提示和自动接口文档。

Flask

Flask

3.1.3 · Windows

轻量灵活的 Python Web 应用框架。

Django

Django

6.1.2 · Windows

成熟的 Python Web 框架,适合构建内容站点和业务系统。

Spyder

Spyder

6.1.7 · Windows

面向科学计算与数据分析的 Python 集成开发环境。

SciPy

SciPy

1.18.1 · Windows

面向科学、工程和技术计算的 Python 算法库。