关于High-Resolution Timer(了解)

如果一个系统包含高精度性能计数器(HRPC,high-resolution performance counter)则此系统提供高精度定时器。你可以使用API函数QueryPerformanceFrequency来获得HRPC的频率HRPCF,返回值为cps(counts per second)。这个依赖于处理器(processor dependent),在一些处理器中HRPCF的值可能就是处理器时钟周期(the cycle rate of the processor clock),比如我们测试,在3.0GHZ的Pentium4处理器(Windows2000 Professional)上得到HSPCF=3000360000,在一个2.8GHZ的Pentium4处理器(Windows XP)上得到HSPCF=2800360000,而在一个2.4GHZ的Pentium4处理器(Windows2000 Server)上得到HSPCF= 3579545。

使用另外一个函数QueryPerformanceCounter来获取(retrieve)HRPC的值,QPF和QPC的函数原型分别为:

BOOL QueryPerformanceFrequency(
LARGE_INTEGER *lpFrequency
);
BOOL QueryPerformanceCounter(
     LARGE_INTEGER *lpPerformanceCount
);
    QPC和QPF函数都在winbase.h中定义。函数中用到的数据类型可以参考如下

typedef __int64 LONGLONG;
typedef unsigned __int64 ULONGLONG
typedef unsigned long DWORD;
 
typedef union union { 
   struct {   
        DWORD LowPart;  
        LONG HighPart; 
   }; 
   LONGLONG QuadPart;
} LARGE_INTEGER, *PLARGE_INTEGER;
在一段代码的前后调用两次HPC函数,就能知道这段代码执行消耗了多少CPU周期或时间,这对于不同算法的性能测试很有帮助,下面有一个例子来进行演示。另外利用循环也可以实现定时功能。

那么怎么根据得到的两个HRPC计算时间呢?因为知道了HRPCF是表示HRPC的频率,所以就可以知道HRPC数值每增加1所代表的时间:

HRPC second per count       dHMSecondPerCount = 1.0   / HRPCF ;  //spc

HRPC millisecond per count  dHMMillisecondPerCount = 1.0E3 / HRPCF ;  //mspc

HRPC microsecond per count  dHMMicrosecondPerCount = 1.0E6 / HRPCF ;  //uspc

知道这三个值就可以根据两个HRPC差值(difference),即diff=HRPC2-HRPC1,这样就可以计算出两次调用QPC函数经过(elapse)的时间:

QueryPerformanceCounter( &HRPC1);

//code to be timed

QueryPerformanceCounter( &HRPC2);

diff=HRPC2-HRPC1;

Elapsed second       = diff * dHMSecondPerCount  ;

Elapsed millisecond  = diff * dHMMillisecondPerCount ;

Elapsed microsecond  = diff * dHMMicrosecondPerCount  ;

例程如下:

/****************************
author:Wandy
time: 2005-11-25
file: demoForHighResolutionTimer.cpp
version:1.0
environment:VS.NET2003 + Windows2000Server
abstract:demo for High-Resolution Timer
*****************************/
#i nclude <windows.h>
#i nclude <stdio.h>
 
void main() {
 
   LARGE_INTEGER liFrequency;
   LARGE_INTEGER liStart;
   LARGE_INTEGER liEnd;
   LONGLONG liDiff;//or LARGE_INTEGER diff;
 
   double dHMSecondPerCount;//how many second per count
   double dHMMillisecondPerCount;//how many millisecond per count
   double dHMMicrosecondPerCount;//how many microsecond per count
  
   //set the current Process and Thresd to a high priority
   DWORD dwOldProcessP = GetPriorityClass(GetCurrentProcess());
   DWORD dwOldThreadP = GetThreadPriority(GetCurrentThread());
   SetPriorityClass(GetCurrentProcess(), REALTIME_PRIORITY_CLASS);
   SetThreadPriority(GetCurrentThread(), THREAD_PRIORITY_TIME_CRITICAL);
 
   // Save the performance counter frequency for later use.
   if ( !QueryPerformanceFrequency( &liFrequency ) )
        printf( "QPF() failed with error %d\n", GetLastError() );
   else
        printf( "HRPCF: %I64d \n",liFrequency.QuadPart );
 
   //
   dHMSecondPerCount      = 1.0    / (double)liFrequency.QuadPart;
   dHMMillisecondPerCount = 1.0E3  / (double)liFrequency.QuadPart;
   dHMMicrosecondPerCount = 1.0E6  / (double)liFrequency.QuadPart;
   printf("dHMSecondPerCount:     %g spc \n", dHMSecondPerCount);
   printf("dHMMillisecondPerCount:%g mspc\n", dHMMillisecondPerCount);
   printf("dHMMicrosecondPerCount:%g uspc\n", dHMMicrosecondPerCount);
    
   //start
   if ( !QueryPerformanceCounter( &liStart ) )
      printf( "QPC() failed with error %d\n", GetLastError() );
   else
        printf( "start HRPC: %I64d \n", liStart.QuadPart );
 
   //code to be timed
   Sleep( 100 );
 
   //end
   if ( !QueryPerformanceCounter( &liEnd ) )
      printf( "QPC() failed with error %d \n", GetLastError() );
   else
      printf( "end HRPC: %I64d \n", liEnd.QuadPart );
 
   //print diff
   liDiff = liEnd.QuadPart - liStart.QuadPart;
 
   printf( "HRPC diff:%I64d and  ms elapsed: %fms\n", liDiff,(double)liDiff * dHMMillisecondPerCount );
 
   //restore the process and thread priority
   SetThreadPriority(GetCurrentThread(), dwOldThreadP);
   SetPriorityClass(GetCurrentProcess(), dwOldProcessP);
 
  
   //wait for press any key
   getchar();
}
在我的机器上的执行结果为
HRPCF: 3579545
dHMSecondPerCount:     2.79365e-007 spc
dHMMillisecondPerCount:0.000279365 mspc
dHMMicrosecondPerCount:0.279365 uspc
start HRPC: 94756807361
end HRPC: 94757165865
HRPC diff:358504 and  ms elapsed: 100.153511ms

 

posted @ 2014-10-12 17:40  zzyoucan  阅读(1354)  评论(0编辑  收藏  举报