我需要将一个进程的结果写入一个txt文件。这个过程很长,要写入的数据量很大(~150Gb)。该程序运行良好,但问题是 RAM 过载,并且在某个时刻,它会停止。
程序很简单:
ostream f;
f.open(filePath);
for(int k=0; k<nDataset; k++){
//treat element of dataset
f << result;
}
f.close();
有没有办法在不超载内存的情况下写入这个文件?
您应该定期刷新输出。
例如:
if (k%10000 == 0) f.flush();
我想建议这样的事情
ogzstream f;
f.open(filePath);
string s("");
for(int k=0; k<nDataset; k++){
//treat element of dataset
s.append(result);
if (s.length() == OPTIMUM_BUFFER_SIZE) {
f << s;
f.flush();
s.clear();
}
}
f << s;
f.flush();
f.close();
基本上,您在内存中构造流而不是重定向到流,因此您不必担心流何时被刷新。并且当您重定向时,请确保它已刷新到实际文件。OPTIMUM_BUFFER_SIZE
可以从这里和这里找到一些想法。
我不确定字符串或向量是否是缓冲区的最佳选择。我自己会做一些研究并更新答案,或者您可以参考 Scott Meyers 的Effective STL。
如果这确实是您的程序卡住的代码,那么您对问题的解释是错误的。
没有文本文件。您igzstream
处理的不是文本,而是gzip
档案。
没有数据被写入。您显示的代码从流中读取。
我不知道你的程序对result做了什么,因为你没有表现出来。但是,如果它将结果累积到内存中的集合中,那将会增长。您需要找到一种方法来处理所有数据,而无需同时将所有数据加载到 RAM 中。
您的内存使用可能来自解压缩器。对于某些压缩算法,必须将整个块存储在内存中。在这种情况下,最好将文件分成块并分别压缩(可能使用前一个块的结果预初始化字典)。但是,我不认为gzip是这样的算法。您可能需要找到支持流式传输的库。