Occasionally I find some useful tricks when programming stuff that can improve performance or otherwise enhance the resulting software. This thread will be used to collect assorted tips and tricks, and you can post your own interesting stuff here too.
Today's tip: MSVC's cout is ridiculously slow. It turns out this is because MSVC doesn't normally buffer cout (and probably cerr) by default.
Solution: Add this to the beginning of your program:
This sets a 4K line buffer for both stdout and stderr. I ran the test program listed at the below MS Connect page, and found that on MSVC 2010, this improves printf() performance by around 1x-1.5x, and cout performance by over 30x. (MSVC 2013 performance with setvbuf() was slightly faster than MSVC 2010, but interestingly it was slower than 2010 if setvbuf() wasn't used.)
(Reference: https://connect.micr...ug-in-c-library )
[NOTE: The referenced page also has a tip for using cout.pubsetbuf(), but on MSVC 2013 at least, if the buffer isn't flushed using endl, MSVCP120 may overflow the buffer, resulting in a crash. It doesn't improve performance that much compared to setvbuf() anyway, so don't bother using it.]
I haven't tested mingw gcc or Linux gcc yet, but I would assume both of those properly buffer stdout and cout. (...actually, considering that's a property of the C library, it'd more appropriately be MSVCRT [which doesn't buffer stdout] and glibc [which might?].)
EDIT: MSVC doesn't actually support line buffering. Enabling line buffering will actually enable full buffering, which may be problematic since printf() on MSVC 2010 doesn't seem to flush the buffer after a newline. endl does flush the buffer. If you're using printf, you can flush the buffer manually using fflush(stdout), but that isn't optimal.
Today's tip: MSVC's cout is ridiculously slow. It turns out this is because MSVC doesn't normally buffer cout (and probably cerr) by default.
Solution: Add this to the beginning of your program:
if (setvbuf(stdout, 0, _IOLBF, 4096) != 0) {
abort();
}
if (setvbuf(stderr, 0, _IOLBF, 4096) != 0) {
abort();
}
This sets a 4K line buffer for both stdout and stderr. I ran the test program listed at the below MS Connect page, and found that on MSVC 2010, this improves printf() performance by around 1x-1.5x, and cout performance by over 30x. (MSVC 2013 performance with setvbuf() was slightly faster than MSVC 2010, but interestingly it was slower than 2010 if setvbuf() wasn't used.)
(Reference: https://connect.micr...ug-in-c-library )
[NOTE: The referenced page also has a tip for using cout.pubsetbuf(), but on MSVC 2013 at least, if the buffer isn't flushed using endl, MSVCP120 may overflow the buffer, resulting in a crash. It doesn't improve performance that much compared to setvbuf() anyway, so don't bother using it.]
I haven't tested mingw gcc or Linux gcc yet, but I would assume both of those properly buffer stdout and cout. (...actually, considering that's a property of the C library, it'd more appropriately be MSVCRT [which doesn't buffer stdout] and glibc [which might?].)
EDIT: MSVC doesn't actually support line buffering. Enabling line buffering will actually enable full buffering, which may be problematic since printf() on MSVC 2010 doesn't seem to flush the buffer after a newline. endl does flush the buffer. If you're using printf, you can flush the buffer manually using fflush(stdout), but that isn't optimal.
This post has been edited by GerbilSoft: 24 July 2014 - 03:39 PM
Reason for edit: +flush warning
Reason for edit: +flush warning


9001