作为一个嵌入式工程师,经常需要使用python写一些脚本工具用于组包测试、通讯测试和算法测试,需要处理很多16进制相关的数据类型,并且要互相转换。于是先初步整理了这一篇文章, 整理了相关常用到的数据类型和相关转换方法,帮助大家理解。
常用的数据类型
- 十六进制字符串(带空格),如 “01 23 45 67 89 ab cd ef”,一般是提供用户界面的数据,获取到的用户输入
- 十六进制字符串(无空格),如"0123456789ABCDEF"
- 十六进制字符串的list,如 [“01”, “23”, “45”, “67”, “89”, “AB”, “CD”, “EF”]
- 十六进制数的list(其实就是数字的list,没有区别),如 [0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF]
- 字节流(两个),但是一旦定义不可更改,如b"\x01\x23\x45\x67\x89\xab\xcd\xef",一般很多校验/加密的方法都需要提供这个格式。此外还有一个struct包,可以实现各种字节流的打包,这个后续再做一篇文章说明。
- ASCII码的字节流,如b"\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x41\x42\x43\x44\x45\x46"
不同数据类型的转换方法
#Obj 1
hex_string = "01 23 45 67 89 ab cd ef"
#Obj 2
hex_string_nospace = "0123456789ABCDEF"
#Obj 3
hex_char_list = ["01", "23", "45", "67", "89", "AB", "CD", "EF"]
#Obj 4
num_list = [0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF]
#Obj 5
bytes_obj = b"\x01\x23\x45\x67\x89\xab\xcd\xef"
#Obj 6 ASCII字节
bytes_obj_ascii = b'0123456789ABCDEF'
#先实现Obj1,Obj2和Obj3的互转
#Obj1转Obj2 , 去除空格,小写变大写
print(hex_string.replace(" ", "").upper())
#将Obj1 转换为 Obj3
print(hex_string.upper().split(" "))
#Obj2转Obj3, 每两个字节显示为一个字符
print([hex_string_nospace[i:i+2] for i in range(0, len(hex_string_nospace), 2)])
#将Obj3 转换为 Obj1
print(" ".join(hex_char_list))
#将Obj3 转换为 Obj4
print([int(x, 16) for x in hex_char_list])
print(num_list)
#将Obj4 转换为 Obj3
print([(hex(x).replace("0x", "").upper() if x >= 0x10 else hex(x).replace("0x", "0").upper()) for x in num_list])
#将Obj2 转换为 Obj5
print(bytes.fromhex(hex_string_nospace))
#将Obj5 转换为 Obj2
print(bytes_obj.hex().upper())
#将Obj2 转换为 Obj6
print(hex_string_nospace.encode("utf-8"))
#将Obj6 转换为 Obj2
print(bytes_obj_ascii.decode("utf-8"))
可以查看运行结果
0123456789ABCDEF
['01', '23', '45', '67', '89', 'AB', 'CD', 'EF']
['01', '23', '45', '67', '89', 'AB', 'CD', 'EF']
01 23 45 67 89 AB CD EF
[1, 35, 69, 103, 137, 171, 205, 239]
[1, 35, 69, 103, 137, 171, 205, 239]
['01', '23', '45', '67', '89', 'AB', 'CD', 'EF']
b'\x01#Eg\x89\xab\xcd\xef'
0123456789ABCDEF
b'0123456789ABCDEF'
0123456789ABCDEF