I discovered by accident that the C++ time()
function runs slowly in programs compiled with Microsoft C++. Consider this example:
#include <iostream>
#include <ctime>
long long unsigned Fib(unsigned n)
{
if (n <= 2)
return 1;
else
return Fib(n-1) + Fib(n-2);
}
int main(int argc, char* argv[])
{
time_t start_time = time(NULL);
// Calculate the first 50 Fibonnaci numbers
for (unsigned i = 1; i <= 50; i++)
std::cout << i << "\t" << Fib(i) << "\t" << difftime(time(NULL), start_time) << std::endl;
// This takes 105 seconds to run, but the last line printed is:
// 50 12586269025 65
return 0;
}
This prints:
1 1 0
2 1 0
...
49 7778742049 40
50 12586269025 65
so difftime(time(NULL), start_time)
is telling me it takes 65 seconds to run, but when I time it with a stopwatch I find it actually takes 105 seconds.
The problem is that the time()
function returns times that run slow. If I print time(NULL)
directly instead of calling difftime()
I can see that the times being printed are lagging behind the actual time. For example if I print time()
instead of difftime()
then when the program finishes I immediately rerun it I find the time jumps forward when I run the program again:
49 7778742049 1611148562
50 12586269025 1611148587
D:\rhs\c>test
1 1 1611148627
2 1 1611148627
Note how the value returned by time()
jumped forward 40 seconds even though it took me only a second to rerun the program.
So my question is why does this happen and how do I fix it (apart from using a different compiler - I have no choice but to use MS C++)? I'm using Visual Studio 2019 so the version of the C++ compiler is Microsoft (R) C/C++ Optimizing Compiler Version 19.28.29335 for x86.
Ah, how embarrassing, it is indeed just order of evaluation in the cout
statement. If I change the loop to:
for (unsigned i = 1; i <= 50; i++)
{
long long unsigned u = Fib(i);
double run_time = difftime(time(NULL), start_time);
std::cout << i << "\t" << u << "\t" << run_time << std::endl;
}
Then it prints the correct elapsed time. Thanks to all who commented. This can be closed as a duplicate.