用C ++获得准确的执行时间(微秒)

时间:2014-02-18 13:57:44

标签: c++ performance

我希望在用C ++实现的程序的微秒内获得准确的执行时间。 我试图用clock_t获得执行时间,但这不准确。

4 个答案:

答案 0 :(得分:65)

如果您使用的是c ++ 11或更高版本,则可以使用std::chrono::high_resolution_clock

一个简单的用例:

auto start = std::chrono::high_resolution_clock::now();
...
auto elapsed = std::chrono::high_resolution_clock::now() - start;

long long microseconds = std::chrono::duration_cast<std::chrono::microseconds>(elapsed).count();

此解决方案具有便携性的优势。

答案 1 :(得分:7)

如果您正在查看从Unix shell执行程序所消耗的时间,请使用Linux time,如下所示,

time ./a.out 

real    0m0.001s
user    0m0.000s
sys     0m0.000s

其次,如果你想在程序代码(C)中执行多少个语句,请尝试使用gettimeofday(),如下所示,

#include <sys/time.h>
struct timeval  tv1, tv2;
gettimeofday(&tv1, NULL);
/* Program code to execute here */
gettimeofday(&tv2, NULL);
printf("Time taken in execution = %f seconds\n",
     (double) (tv2.tv_usec - tv1.tv_usec) / 1000000 +
     (double) (tv2.tv_sec - tv1.tv_sec));

答案 2 :(得分:1)

如果您使用的是Windows,则可以使用QueryPerformanceCounter

请参阅How to use the QueryPerformanceCounter function to time code in Visual C++

__int64 ctr1 = 0, ctr2 = 0, freq = 0;
int acc = 0, i = 0;

// Start timing the code.
if (QueryPerformanceCounter((LARGE_INTEGER *)&ctr1)!= 0)
{
    // Code segment is being timed.
    for (i=0; i<100; i++) acc++;

    // Finish timing the code.
    QueryPerformanceCounter((LARGE_INTEGER *)&ctr2);

    Console::WriteLine("Start Value: {0}",ctr1.ToString());
    Console::WriteLine("End Value: {0}",ctr2.ToString());

    QueryPerformanceFrequency((LARGE_INTEGER *)&freq);

    Console::WriteLine(S"QueryPerformanceCounter minimum resolution: 1/{0} Seconds.",freq.ToString());
    // In Visual Studio 2005, this line should be changed to:     Console::WriteLine("QueryPerformanceCounter minimum resolution: 1/{0} Seconds.",freq.ToString()); 
    Console::WriteLine("100 Increment time: {0} seconds.",((ctr2 - ctr1) * 1.0 / freq).ToString());
}
else
{
    DWORD dwError = GetLastError();
    Console::WriteLine(S"Error value = {0}",dwError.ToString());// In Visual Studio 2005, this line should be changed to: Console::WriteLine("Error value = {0}",dwError.ToString());
}

// Make the console window wait.
Console::WriteLine();
Console::Write("Press ENTER to finish.");
Console::Read();

return 0;

您可以在整个流程生命周期内调用CreateProcess(...)WaitForSingleObject(...),否则围绕代码的主要功能。

答案 3 :(得分:1)

新的C ++ 11 std::chrono库是我见过或试图弄清楚如何使用的最复杂的混乱之一,但至少它是跨平台的!

所以,如果你想简化它并使其更像“C”和“#34;”,包括删除它所做的所有类型安全类的东西,这里&#39 ; s 3个简单且易于使用的函数,以毫秒,微秒和纳秒为单位获取时间戳 ...只花了我大约12小时来编写*:

#include <chrono>

// NB: ALL OF THESE 3 FUNCTIONS BELOW USE SIGNED VALUES INTERNALLY AND WILL EVENTUALLY OVERFLOW (AFTER 200+ YEARS OR
// SO), AFTER WHICH POINT THEY WILL HAVE *SIGNED OVERFLOW*, WHICH IS UNDEFINED BEHAVIOR (IE: A BUG) FOR C/C++.
// But...that's ok...this "bug" is designed into the C++11 specification, so whatever. Your machine won't run for 200
// years anyway...

// Get time stamp in milliseconds.
uint64_t millis()
{
    uint64_t ms = std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::
                  now().time_since_epoch()).count();
    return ms; 
}

// Get time stamp in microseconds.
uint64_t micros()
{
    uint64_t us = std::chrono::duration_cast<std::chrono::microseconds>(std::chrono::high_resolution_clock::
                  now().time_since_epoch()).count();
    return us; 
}

// Get time stamp in nanoseconds.
uint64_t nanos()
{
    uint64_t ns = std::chrono::duration_cast<std::chrono::nanoseconds>(std::chrono::high_resolution_clock::
                  now().time_since_epoch()).count();
    return ns; 
}

* (对不起,我是一个嵌入式开发人员,而不是标准的计算机程序员,因此所有这些高级,抽象的静态成员都在命名空间内的命名空间内 - 命名空间内的东西让我感到困惑。别担心,我会变得更好。)

以下是一些参考文献: