优化:在 C 或 C++ 中缩小文件大小

Optimisation: Shrinking file size in C or C++

在对具有 n(例如 10000)个粒子的系统进行计算机模拟时,通常的工作流程涉及以给定的时间间隔频繁保存系统状态。这需要在文件中写下所有粒子的位置坐标(因此每行 3 floats/doubles,每行一个粒子),以及一些 header 信息。浮动精度设置为固定值。

我通常 save/write 配置文件的方式如下(调用时创建文件的函数的一部分):

#include <iostream>
#include <fstream>

ofstream outfile(filelabel, ios::out);
outfile.precision(10);

outfile << "#Number of particles " << npart << endl;

for (int i=0; i<npart; i++){
outfile << particle[i].pos[0] << " " << particle[i].pos[1] << " " << particle[i].pos[2] << endl;
}

outfile.close();

通常情况下,对于足够大的系统,每个此类文件的大小为 0.5-4 MB,因此当经常保存它们时,它们最终会加起来很大。所以我正在尝试学习如何将配置文件的大小优化到最低限度,例如通过(想到的 2 个想法):

任何有关如何在 C/C++ 可能性范围内缩小配置文件大小的建议和建议,我们将不胜感激。


小补

根据目前的建议,二进制格式的保存似乎是一种很好的替代方法,但是,作为一个 follow-up 问题,是否可以在 Python 例如?

这与保存的配置文件相关,我倾向于将 Python 用于 post-analysis 目的。

四点建议:

  1. 保存矢量信息(方向和偏移)比保存 X-Y-Z 坐标花费的时间更少 space。但这意味着保留对初始状态文件的引用——这需要更多的计算。

  2. 假设上述方法不实用,那么如果存储space比计算时间更重要,我仍然会考虑使用向量。 3D 矢量以 2 个值而不是三个值对位置进行编码,因此即使您从原点而不是粒子的先前位置引用所有位置,文件也应该小近 30%(假设存储矢量需要更高的精度) .

  3. 位置坐标如何"random"?如果有一些相关性,那么我会将数据保存在文本中并使用无损文件压缩方法(例如建议将文件保存在支持文件系统压缩的磁盘上 - 这意味着 no为你工作!)任何重复的字符串都会被压缩并且可能比二进制文件更有效 - 如果数据有重复的字符串。如果坐标出现伪随机,则压缩(如 ZIP 格式)不会给您带来任何好处,您应该使用二进制值方法。

  4. 如果以二进制形式存储(甚至可能以文本形式),请考虑在将浮点值写入文件之前将浮点值转换为适合 volume/precision 的整数。这比存储浮点(或更糟的双精度)值花费的 space 少得多。这当然假设您需要的精度可以在 int(或 long)的精度内表示。