This problem is to test how fast you are able to read the input. Faster input output methods are required for some problems in UVa, SPOJ, CodeChef and other sites (Usually the problem statements have a warning that the IO is huge).
What I found out about faster IO:
Never use cin or cout. Always use scanf and printf (they are about twice faster). But there are methods much much faster than scanf and printf!!
My first solution to the above problem: was using scanf and printf. -->Execution time: 5.44 s
Then I googled to find out this function to read integers using getchar:
inline void fastRead(int *a)
{
register char c=0;
while (c<33) c=getchar();
*a=0;
while (c>33)
{
*a=*a*10+c-'0';
c=getchar();
}
}
I used it and my execution time became reduced by 2 seconds to 3.40 s
I then stumbled upon UVa forum where someone suggested that getchar_unlocked is faster than getchar. So I modified the function to use getchar_unlocked:
inline void fastRead(int *a)
{
register char c=0;
while (c<33) c=getchar_unlocked();
*a=0;
while (c>33)
{
*a=*a*10+c-'0';
c=getchar_unlocked();
}
}
I submitted the program again with the getchar_unlocked modification and my execution time is now believe it or not: 0.76 s
Check this out:
10 comments:
wow, i was looking for the faster input output method and this is awesome .
And i also heard fread function is much faster . is it ?
and please keep posted new things .
Hi,
Can you please help me understand the function fastRead?I am not getting how the two while loops are working.
Thanks everyone for comments...
@Amit
Fread reads blocks of data at once... so I think should be faster. Should try it out :P
@Anonymous
To read an integer x, call the function like this:
fastRead(&x);
What it does:
The ascii value of '\n' is 10.
The ascii value of ' ' is 32.
The function reads all the empty lines and spaces till it encounters a digit. (while (c<33))
If the input is like this:
(newline)
(space)(space)123
The function reads all the newlines and spaces till it encounters the character '1'.
From then, it builds the integer character by character like this:
0 (initial value)
1 (shifts 0 to the left(to get 0) and adds the first character)
10 + 2 (shifts 1 to the left(to get 10) and adds the second character)
120 + 3 (shifts 12 to the left(to get 120) and adds the third character)
And it continues reading till it encounters a space or '\n' signifying the end of the number. (while(c>33))
Note:
Since every digit is a character, it is in ASCII. ie., '0' is 48, '1' is 49, and so on...
Therefore to get the number 1 from character '1', we have to subtract 48 or '0'.
great explainations.......
Very useful post. Thanks bro
Can you please explain what the two while loops are used for??
Really awesome and helpful post , but can somebody give an example on how to implement it ?
really very nice
awesome
really helping
Post a Comment