Saturday 17 December 2016

C++ getline() slower than Java's readLine()





I'm trying to read a 250K line file, and apply regex to each of these lines. However the code is much much slower than Java's readline function. In Java all the parsing is done in ~10 sec, while in C++ it takes more than 2 mins. I've seen the relative C++ ifstream.getline() significantly slower than Java's BufferedReader.readLine()? and added these two lines on top of main:



std::ifstream::sync_with_stdio(false);
std::ios::sync_with_stdio(false);


The rest of the code (I simplified it to remove any delays regex might be causing):



#include "stdafx.h"
#include

#include
#include
#include


int _tmain(int argc, _TCHAR* argv[])
{

std::string libraryFile = "H:\\library.txt";
std::ios::sync_with_stdio(false);

std::string line;

int i = 1;

std::ifstream file(libraryFile);
while (std::getline (file, line)) {
std::cout << "\rStored " << i++ << " lines.";
}

return 0;

}


The example seems quite simple, but even the fix suggested in most posts doesn't seem to work. I've run the .exe multiple times using release settings in VS2012, but I just can't reach Java's times.


Answer



The slowness is caused by a couple of things.




  • Mixing cout and cin: The C++ IO library has to synchronize cout every time cin is used. This is to ensure things like input prompts are displayed before asking for input. This really hurts buffering.


  • Using the Windows console output: The Windows console is so slow, especially while doing terminal emulation, that it isn't funny. If at all possible output to a file instead.




No comments:

Post a Comment

c++ - Does curly brackets matter for empty constructor?

Those brackets declare an empty, inline constructor. In that case, with them, the constructor does exist, it merely does nothing more than t...