精确的时间测量

时间:2013-01-15 12:02:20

标签: c++ visual-studio-2010 chrono ctime

我在C ++中使用time.h来测量函数的时间。

clock_t t = clock();
someFunction();
printf("\nTime taken: %.4fs\n", (float)(clock() - t)/CLOCKS_PER_SEC);

然而,我总是把时间花在0.0000上。 clock()和t单独打印时,具有相同的值。我想知道是否有办法在C ++中精确测量时间(可能是纳秒级)。我正在使用VS2010。

4 个答案:

答案 0 :(得分:91)

C ++ 11引入了chrono API,你可以用来获得纳秒:

auto begin = std::chrono::high_resolution_clock::now();

// code to benchmark

auto end = std::chrono::high_resolution_clock::now();
std::cout << std::chrono::duration_cast<std::chrono::nanoseconds>(end-begin).count() << "ns" << std::endl;

对于更相关的值,最好多次运行该函数并计算平均值:

auto begin = std::chrono::high_resolution_clock::now();
uint32_t iterations = 10000;
for(uint32_t i = 0; i < iterations; ++i)
{
    // code to benchmark
}
auto end = std::chrono::high_resolution_clock::now();
auto duration = std::chrono::duration_cast<std::chrono::nanoseconds>(end-begin).count();
std::cout << duration << "ns total, average : " << duration / iterations << "ns." << std::endl;

但请记住for循环并分配beginend var也会占用一些CPU时间。

答案 1 :(得分:55)

我通常使用QueryPerformanceCounter函数。

示例:

LARGE_INTEGER frequency;        // ticks per second
LARGE_INTEGER t1, t2;           // ticks
double elapsedTime;

// get ticks per second
QueryPerformanceFrequency(&frequency);

// start timer
QueryPerformanceCounter(&t1);

// do something
...

// stop timer
QueryPerformanceCounter(&t2);

// compute and print the elapsed time in millisec
elapsedTime = (t2.QuadPart - t1.QuadPart) * 1000.0 / frequency.QuadPart;

答案 2 :(得分:6)

我完全同意的以下文字引自Optimizing software in C++(任何C ++程序员的好读物) -

  

如果时间过长,时间测量可能需要非常高的分辨率   间隔很短。在Windows中,您可以使用   GetTickCount或   QueryPerformanceCounter以毫秒级分辨率运行。很多   使用时间戳计数器可以获得更高的分辨率   CPU,以CPU时钟频率计数。

存在“时钟频率可能动态变化的问题 由于中断和任务切换,测量结果不稳定。“

答案 3 :(得分:2)

在C或C ++中,我通常会在下面做。如果仍然失败,您可以考虑使用rtdsc函数

      struct timeval time;
      gettimeofday(&time, NULL); // Start Time

      long totalTime = (time.tv_sec * 1000) + (time.tv_usec / 1000);

          //........ call your functions here

        gettimeofday(&time, NULL);  //END-TIME

        totalTime = (((time.tv_sec * 1000) + (time.tv_usec / 1000)) - totalTime);