(MATLAB/C/Python)读写二进制文件
最近我一朋友被文件的读写所困扰,不同平台不同格式不同类型,C写M读、M写C读……
C就不说了,MATLAB就读文件的函数就有一堆:TEXTREAD, TEXTSCAN, STRREAD, DLMREAD, LOAD, SSCANF, FREAD等,每个参数也是各不相同。
要我说如果仅仅是自己个人使用,用作不同语言不同平台间传递数据,最好还是使用二进制格式,“0/1”是我们值得信赖的伙伴。所以在这里分享MATLAB和C语言,将不同类型数据保存为二进制的方法。
by HPC_ZY
一、数据类型简介
C类型 | 对应M类型 | 字节数 | 位数 |
---|---|---|---|
char | char | 1 | 8 |
BYTE | uint8 | 1 | 8 |
int | int32 | 4 | 32 |
float | single | 4 | 32 |
double | double | 8 | 64 |
二、MATLAB读写二进制数据
- 先来生成一个测试数据
% 测试数据
A = [0,1,2,4,16,64,128,255]
- uint8(c-byte)类型数据
%% byte
data = uint8(A);
% write
fp = fopen('.\data.byte','wb');
fwrite(fp,data);
fclose(fp);
% read
fp = fopen('.\data.byte','rb');
data = fread(fp,'bit8=>uint8');
fclose(fp);
- int32(c-int)类型数据
%% int
data = int32(A);
% write
fp = fopen('.\data.int','wb');
fwrite(fp,data,'int32');
fclose(fp);
% read
fp = fopen('.\data.int','rb');
data = fread(fp,'int32=>int32');
fclose(fp);
- single(c-flaot)类型数据
%% float
data = single(A);
% write
fp = fopen('.\data.float','wb');
fwrite(fp,data,'single');
fclose(fp);
% read
fp = fopen('.\data.float','rb');
data = fread(fp,'single=>single');
fclose(fp);
- double类型
%% double
data = double(A);
% write
fp = fopen('.\data.double','wb');
fwrite(fp,data,'double');
fclose(fp);
% read
fp = fopen('.\data.double','rb');
data = fread(fp,'double=>double');
fclose(fp);
三、C读写二进制数据
// 设置一个小的尺寸方便测试
int N = 16;
- BYTE(m-uint8)类型数据
// 生成数据
BYTE *data = (BYTE*)malloc(N * sizeof(BYTE));
for (int i = 0; i < N; i++)
{
data[i] = i;
}
// 写文件
FILE* fp = fopen("D:\\data.BYTE", "wb");
fwrite(data, 1, N, fp);
fclose(fp);
// 读文件
BYTE *datain = (BYTE*)malloc(N * sizeof(BYTE));
fp = fopen("D:\\data.BYTE", "rb");
fread(datain, sizeof(BYTE), N, fp);
fclose(fp);
// 显示
for (int i = 0; i < N; i++)
{
printf("%d\n", data[i]);
}
- int(m-int32)类型数据
// 生成数据
int *data = (int*)malloc(N * sizeof(int));
for (int i = 0; i < N; i++)
{
data[i] = i;
}
// 写文件
FILE* fp = fopen("D:\\data.int", "wb");
fwrite(data, 1, N, fp);
fclose(fp);
// 读文件
int *datain = (int*)malloc(N * sizeof(int));
fp = fopen("D:\\data.int", "rb");
fread(datain, sizeof(int), N, fp);
fclose(fp);
// 显示
for (int i = 0; i < N; i++)
{
printf("%d\n", data[i]);
}
- flaot(c-single)类型数据
// 生成数据
float *data = (float*)malloc(N * sizeof(float));
for (int i = 0; i < N; i++)
{
data[i] = i;
}
// 写文件
FILE* fp = fopen("D:\\data.float", "wb");
fwrite(data, 1, N, fp);
fclose(fp);
// 读文件
float *datain = (float*)malloc(N * sizeof(float));
fp = fopen("D:\\data.float", "rb");
fread(datain, sizeof(float), N, fp);
fclose(fp);
// 显示
for (int i = 0; i < N; i++)
{
printf("%.2f\n", data[i]);
}
- double类型
// 生成数据
double *data = (double*)malloc(N * sizeof(double));
for (int i = 0; i < N; i++)
{
data[i] = i;
}
// 写文件
FILE* fp = fopen("D:\\data.double", "wb");
fwrite(data, 1, N, fp);
fclose(fp);
// 读文件
double *datain = (double*)malloc(N * sizeof(double));
fp = fopen("D:\\data.double", "rb");
fread(datain, sizeof(double), N, fp);
fclose(fp);
// 显示
for (int i = 0; i < N; i++)
{
printf("%.2f\n", data[i]);
}
四、Python读写二进制
- float类型
# data
data = np.array([1.5, 2.74, 5.99, 11.87]).astype(np.float32)
# write
filename = 'data.raw'
file = open(filename, 'wb')
file.write(data)
file.close()
# read
file = open(filename, 'rb')
dataB = file.read()
num = int(len(dataB)/4)
dataF = struct.unpack('f'*num, dataB)
file.close()
print(data)
print(dataB)
print(dataF)
五、特殊示例
- logical类型
只有true和false,感觉它只占一位二进制(8个占一个字节),但实际上通过如下测试发现,它在内存中占8个字节,直接写成文件后同样占8个字节。
data = logical([0,1,0,1,0,1,0,1]);
% write
fp = fopen('.\data.bin','wb');
fwrite(fp,data);
fclose(fp);
其他
- 预计下周一全部完成,先把写好的分享出来