I have several questions about new <chrono>
header in C++ 11. Using Windows 7, Visual Studio 2012.
Looking at the example http://en.cppreference.com/w/cpp/chrono
#include <iostream>
#include <chrono>
#include <ctime>
int fibonacci(int n)
{
if (n < 3) return 1;
return fibonacci(n-1) + fibonacci(n-2);
}
int main()
{
std::chrono::time_point<std::chrono::system_clock> start, end;
start = std::chrono::system_clock::now();
int result = fibonacci(42);
end = std::chrono::system_clock::now();
int elapsed_seconds = std::chrono::duration_cast<std::chrono::seconds>
(end-start).count();
std::time_t end_time = std::chrono::system_clock::to_time_t(end);
std::cout << "finished computation at " << std::ctime(&end_time)
<< "elapsed time: " << elapsed_seconds << "s\n";
}
Possible output
finished computation at Sat Jun 16 20:42:57 2012
elapsed time: 3s
std::chrono::system_clock::now();
does it mean it can be used to measure only elapsed time and not the CPU time ??? And if I want to measure CPU time, what Clocks should I use ? elapsed time: 3s
is output is rounded to whole integer. Is there way to make it more granulated?The <chrono> library is part of the C++ date and time utilities. <chrono> is also the name of a namespace, so all objects defined inside the library are under the std::chrono namespace instead of the standard namespace.
(since C++11) Class template std::chrono::duration represents a time interval. It consists of a count of ticks of type Rep and a tick period, where the tick period is a compile-time rational fraction representing the time in seconds from one tick to the next.
std::chrono::system_clock::now Returns a time point representing with the current point in time.
class Duration = typename Clock::duration. > class time_point; (since C++11) Class template std::chrono::time_point represents a point in time. It is implemented as if it stores a value of type Duration indicating the time interval from the start of the Clock 's epoch.
Correct
According to the standard:
system_clock represent[s] wall clock time from the system-wide realtime clock.
The <chrono>
library does not provide a mechanism for measuring CPU time, so if you want that you'll have to fall back on the old <ctime>
library and use std::clock()
.
(And if you're targeting Windows you'll have to fall back on whatever platform-specific API Windows provides for getting CPU time since, as you point out, their std::clock()
doesn't work correctly.)
system_clock
is more like a counterpart to std::time()
than to std::clock()
. (E.g., note that system_clock
provides conversions between system_clock::time_point
s and time_t
.) I imagine that the lack of a clock in <chrono>
for measuring CPU time is due to time constraints on the standard committee and the fact that that functionality is less used than the system's wall clock and real-time clocks.
If you want CPU time but also want the benefits that <chrono>
provides, you should implement a clock type that conforms to the Clock concept outlined in the standard and which provides CPU time, perhaps implemented internally using std::clock()
.
The line that says
int elapsed_seconds = std::chrono::duration_cast<std::chrono::seconds> (end-start).count();
is what causes the time to be rounded to an integral number of seconds. You can choose any period you'd like, or you can use a floating point representation in order to allow non-integral values:
std::int64_t elapsed_attoseconds =
std::chrono::duration_cast<std::chrono::duration<std::int64_t, std::atto>>
(end-start).count();
double elapsed_seconds =
std::chrono::duration_cast<std::chrono::duration<double,std::ratio<1>>>
(end-start).count();
Note that in real code you should avoid using .count()
to escape the strong typing provided by chrono::duration
until you absolutely must.
auto total_duration = end - start;
auto seconds = std::chrono::duration_cast<std::chrono::seconds>(total_duration);
auto milli = std::chrono::duration_cast<std::chrono::milliseconds>(total_duration - seconds);
std::cout << seconds.count() << "s " << milli.count() << "ms\n";
1) I'm fairly certain the highest resolution you can get is to use std::chrono::high_resolution_clock
and then don't do any duration casting:
int elapsed_ticks = (end-start).count();
2) Change the argument of duration_cast to something like nanoseconds
:
int elapsed_seconds = std::chrono::duration_cast<std::chrono::nanoseconds>
(end-start).count();
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With