一、前言
背景:很多时候我们需要用python处理二进制数据。例如,存储文件、进行socket操作等。这个时候就需要用到struct模块。
struct用途:
(1)按照指定格式将Python数据转换为字符串(字节流)。如网络传输时不能直接传输int/long数据,此时要先将int/long转化为字节流,然后再发送;
(2)按照指定格式将字节流转换为Python指定的数据类型;
(3)处理二进制数据,如果用struct来处理文件的话,需要用’wb’,’rb’以二进制(字节流)写,读的方式来处理文件;
(4)处理C或者C++语言中的结构体;
接下来我们介绍struct模块中最重要的pack,unpack两个函数。
注:例如二进制流与数值的互相转换在编解码、开发小工具方面用途非常广泛。
二、struct模块
1、pack()函数
#按照给定的格式(format),把数据封装成字符串(实际上是类似于C结构体的字节流)
pack(format,v1,v2,...)
2、unpack()函数
#按照给定的格式(format),解析字节流string,返回解析出来的tuple
pack(format,string)
3、calcsize()函数
#计算给定的格式(format)占用多少字节的内存。
#注:icc表示三个成员数据类型是interger, char, char。
size = struct.calcsize(’@icc’) 结果是6。
size = struct.calcsize(’@cic’) 结果是9。
4、上述format支持的格式参见末尾表格。关于格式有如下几点说明:
(1)每个格式前面可以带一个数字,表示个数;
(2)s格式表示一定长度的字符串,4s表示长度为4的字符串;
(3)P用来转换一个指针,其长度和机器字长相关;
5、为了同C结构体交换数据还要考虑C或者C++编译器用到的字节对齐。字节序和对齐方式有如下5种:
Character | Byte order | Size | Alignment |
---|---|---|---|
@(默认) | 本机 | 本机 | 本机,凑够4字节 |
= | 本机 | 标准 | none,按原字节数 |
< | 小端 | 标准 | none,按原字节数 |
> | 大端 | 标准 | none,按原字节数 |
! | network(大端) | 标准 | none,按原字节数 |
(1)Byte order列中的native(本机)表示和当前系统的字节序一致;
(2)size列的native(本机)表示这个时候数据类型的大小和sizeof一致;如果是standard(标准)表示数据类型的长度是固定的;
(3)alignment是native(本机)的时候表示和当前系统的字节对齐方式一致。但是要注意的是python中的字节填充(padding)只会在连续的结构体成员之间添加,不会在结构体的开头和结尾添加。例如:
size = struct.calcsize(’@icc’) 结果是6。
size = struct.calcsize(’@cic’) 结果是9。