Updated: Add note for Cygwin environment.
Updated: Add result on FreeBSD
In programming competition such as Codeforces, reading a large number of inputs is somtimes required, for example, 1500*1500 integers in Codeforces Beta Round #43 Problem E. I used iostream(cin) in the competition and got TLE. After the competition, I saw some comments that cin caused TLE. After I replaced cin with scanf, I got AC. So, it is said "For large input, use cstdio instead of iostream." However I believe C++ users want to use iostream. Can't we avoid the guideline?
I found one promising way. Unfortunately, it is applicable not to VC but to gcc. Call std::ios_base::sync_with_stdio(false) at the beginning of your code. Here is the graph to show performance comparison among iostream with the call, without the call and cstdio, in my local environments. [Updated: NOTE that File I/O on Cygwin is generally very slow. Therefore, the effect is overestimated in graph on Cygwin environment.]
X-axis shows the number of inputs and Y-axis shows seconds to read inputs. The scale of Y-axis is different between graphs.
The summary of my local environment is as follows:
- CPU: Core2Duo T7600 2.3Ghz
- RAM: 4GB
- OS: Windows XP SP3
- Compiler: gcc 4.3.4 on Cygwin 1.7.7
- CPU: PentiumM 1.3GHz
- RAM: 1GB
- OS: FreeBSD 8.1-STABLE
- Compiler: gcc 4.2.1
Target source code is here (at codepad.org).
Though I don't know the precise effect in the judge environment, I can get AC with iostream, at least, for Codeforces Beta Round #43 Problem E. NOTE that the effect of the call depends on implementation of C++ standard library. For example, there is no significant difference for VC++.
Calling sync_with_stdio(false) may improve performance. What is the actual effect of the call?
The standard (ISO/IEC 14882:2003) says:
22.214.171.124 ios_base static members
bool sync_with_stdio(bool sync = true);
Returns: true if the standard iostream objects (27.3) are synchronized and otherwise returns false.
The first time it is called, the function returns true.
Effects: If any input or output operation has occurred using the standard streams prior to the call, the effect is implementation-defined. Otherwise, called with a false argument, it allows the standard streams to operate independently of the standard C streams.
This means that synchronization with standard C stream is required without the call. In libstdc++ (C++ standard library used by g++), this flag switches iostream object's underlying buffer between stdio_filebuf and stdio_sync_filebuf. stdio_sync_filebuf has little buffering by itself and delegate almost all operation to cstdio. See also libstdc++ manual page.
For programming competition, there seems to be little use of mixture of cstdio and iostream. Thus, I recommend that you include the call in your code template. :p