I needed a portable C++ milliseconds alternative to the Microsoft Windows GetTickCount
API, to work on g++ in Linux and OS X, and I also wanted to fix the elapsed time span rollover issue that occurs when you subtract one tick count from another.
Use the GetMilliCount
and GetMilliSpan
functions as follows:
int nTimeStart = GetMilliCount(); // ... processing int nTimeElapsed = GetMilliSpan( nTimeStart );
This is better than using GetTickCount
and subtracting the first tick count from the second since that is subject to the rollover issue described below.
Here are the functions you can copy and paste into your code (32-bit int
is assumed).
#include <sys/timeb.h> int GetMilliCount() { // Something like GetTickCount but portable // It rolls over every ~ 12.1 days (0x100000/24/60/60) // Use GetMilliSpan to correct for rollover timeb tb; ftime( &tb ); int nCount = tb.millitm + (tb.time & 0xfffff) * 1000; return nCount; } int GetMilliSpan( int nTimeStart ) { int nSpan = GetMilliCount() - nTimeStart; if ( nSpan < 0 ) nSpan += 0x100000 * 1000; return nSpan; }
Note that the maximum millisecond span is about 12.1 days to provide a convenient cutoff in the tb.time
seconds to milliseconds calculation.
GetMilliCount
, like GetTickCount
, returns a number of milliseconds that starts over (rolls over) when it reaches a maximum. If you subtract an earlier count from a later count, there is a risk of the rollover occuring in the interim, giving an incorrect millisecond span.
GetMilliSpan
corrects for the rollover by doing an extra check to see if the rollover occurred in the interim.
Using the timeb
structure and the ftime
function, it is possible to obtain millisecond counts beyond the 49.7 day limit of GetTickCount
and 32-bit integers.
I considered using a 64-bit integer (VC++ __int64
or g++
int64_t
) which can handle 500 billion years of milliseconds. But 64-bit integers introduce additional portability issues.
Generally you want to know how long an action takes from a fraction of a second to a few seconds. In rare cases you might want to measure hours or days with milliseconds in C++. The GetMilliCount
limit of 12.1 days is plenty for most purposes.
The solution shown here is okay for easily giving the user feedback on how long something took, such as how long it took to parse or save a document. But system clock milliseconds is not the most accurate way to measure performance.
The time a process takes to perform an activity is affected by other system usage, plus the clock ticks are generally multiple milliseconds and don't give you the granularity to estimate actual CPU usage.
For more accurate timing information, look for code performance profiling solutions or a high resolution performance counter like Windows QueryPerformanceCounter
which returns a 64-bit LARGE_INTEGER
.
It is public domain, use at will, include in your open source project, etc. Best wishes.
Mark Plunkett 09-Apr-2009
I'm developing some software for a university final year project and I found your
GetTickCount
alternative very useful, I am just enquiring as to whether it falls under any license, and whether it is ok to include in my project, which I am planning to open source upon completion?