c++ ostringstream改进IO性能

c++ ostringstream improve IO performance?

本文关键字:性能 IO 改进 ostringstream c++      更新时间:2023-10-16

当我尝试将一些字符串写入文件时,我注意到使用ostringstream可以提高性能。

下面的代码做了以下事情:
1. 生成一些随机字符串
2. 使用ostringstream
将其写入文件3.使用ofstream

将其写入文件
#include <vector>
#include <sstream>
#include <fstream>
#include <iostream>
#include <sys/time.h>
using namespace std;
double timeGetTimeOfDay(){
    struct timeval t;
    gettimeofday(&t, NULL);
    return double(t.tv_sec) + double(t.tv_usec) / 1000000;
}
string genRandString(int length){
    string r;
    for(int i=0; i<length; i++)
        r.push_back(char('a' + rand()%26));
    return r;
}
void genRandStrings(vector<string>& allStrings, int count, int length){
    srand(unsigned(time(NULL)));
    for(int i=0; i<count; i++)
        allStrings.push_back(genRandString(length));
}
int main(){
    ofstream fout("temp");
    vector<string> allStrings;
    genRandStrings(allStrings, 100000, 100);
    // output method1
    double start = timeGetTimeOfDay();
    ostringstream os;
    for(int i=0; i<allStrings.size(); i++)
        os<<allStrings[i]<<endl;
    fout<<os.str();
    double end = timeGetTimeOfDay();
    cout<<end - start<<endl;
    // output method2
    start = timeGetTimeOfDay();
    for(int i=0; i<allStrings.size(); i++)
        fout<<allStrings[i]<<endl;
    end = timeGetTimeOfDay();
    cout<<end - start<<endl;
    fout.close();
    return 0;
}

在我的计算机上,ostringstream使用0.016933秒,但ofstream使用0.132003秒

我不知道为什么会这样?
是因为使用ostringstream减少了IO的数量吗?
是否std::ofstream有一个缓冲区来减少IO的数量?或者每次使用fout<<都是IO?
那么,我们是否可以将其推广到提高从文件读取的性能呢?

第二个方法由于std::endl(它会放入换行符并刷新流)而失败了内部缓冲。

通过将std::endl替换为n并在写入所有数据后刷新流,第二个方法比第一个方法更快(字符串流成为额外的开销)。

int main(){
    vector<string> allStrings;
    genRandStrings(allStrings, 100000, 100);
    // output method1
    {
        ofstream fout("temp1");                       // Distinct output file
        double start = timeGetTimeOfDay();
        ostringstream os;
        for(unsigned i=0; i<allStrings.size(); i++)
            os<<allStrings[i]<<'n';                  // New line, only
        fout << os.str();
        fout.flush();                                 // Flushing output
        double end = timeGetTimeOfDay();
        cout<<end - start<<endl;
    }
    // output method2
    {
        ofstream fout("temp2");                       // Distinct output file
        double start = timeGetTimeOfDay();
        for(unsigned i=0; i<allStrings.size(); i++)
            fout<<allStrings[i]<<'n';                // New line, only
        fout.flush();                                 // Flushing output
        double end = timeGetTimeOfDay();
        cout<<end - start<<endl;
    }
    return 0;
}

使用c++ -std=c++14 -O3编译的系统上的结果:

0.025744
0.0173609