是有什么区别std::system_clock
和std::steady_clock
? (即示出了不同的结果的一个例子的情况下/行为将是巨大的)。
如果我的目标是精确测量的功能(如基准)的执行时间,这将是之间最好的选择std::system_clock
, std::steady_clock
和std::high_resolution_clock
?
是有什么区别std::system_clock
和std::steady_clock
? (即示出了不同的结果的一个例子的情况下/行为将是巨大的)。
如果我的目标是精确测量的功能(如基准)的执行时间,这将是之间最好的选择std::system_clock
, std::steady_clock
和std::high_resolution_clock
?
从N3376:
20.11.7.1 [time.clock.system] / 1:
类的对象
system_clock
表示来自全系统的实时时钟挂钟时间。
20.11.7.2 [time.clock.steady] / 1:
类的对象
steady_clock
表示为其值时钟time_point
从不减少为物理时间的进步和对其中的值time_point
以相对于实时稳定的速率前进。 也就是说,时钟可以不调整。
20.11.7.3 [time.clock.hires] / 1:
类的对象
high_resolution_clock
表示具有最短周期蜱时钟。high_resolution_clock
可以是用于同义词system_clock
或steady_clock
。
例如,系统级时钟可能通过类似日光节约时间,在这点在未来的某个时候上市的实际时间实际上是在过去一段时间受到影响。 (例如,在美国,在秋季时间快一小时,所以同一时刻是经历了“两次”)然而, steady_clock
是不允许被这样的事情所影响。
在这种情况下考虑“稳定”的另一种方法是在的20.11.3 [time.clock.req] / 2表中定义的要求:
在表59
C1
和C2
表示时钟类型。t1
和t2
是通过返回的值C1::now()
当调用返回t1
呼叫前发生回t2
之前这两个电话的出现C1::time_point::max()
[注:这意味着C1
并不环绕之间的t1
和t2
。 末端注]表达:
C1::is_steady
返回:const bool
操作语义:true
如果t1 <= t2
始终为真和时钟之间的时间刻度是恒定的,否则false
。
这是所有的标准对他们之间的分歧。
如果你想要做标杆,你最好的选择可能是将要std::high_resolution_clock
,因为它很可能是你的平台使用高分辨率定时器(如QueryPerformanceCounter
这个时钟在Windows上)。 但是,如果你标杆,你真的应该考虑使用特定于平台的定时器为您的基准,因为不同的平台上处理这种不同。 例如,一些平台可能会给你的确定时钟的实际数目的一些手段蜱(独立于同一个CPU上运行的其他进程的)所需的程序。 更重要的是,得到一个真正的探查你的手和使用。
比利提供基于ISO C ++标准,我完全同意一个伟大的答案。 然而,有故事的另一面 - 真实的生活。 看来,现在真的是有在实现流行的编译器的那些时钟之间没有什么区别:
GCC 4.8:
#ifdef _GLIBCXX_USE_CLOCK_MONOTONIC
...
#else
typedef system_clock steady_clock;
#endif
typedef system_clock high_resolution_clock;
的Visual Studio 2012:
class steady_clock : public system_clock
{ // wraps monotonic clock
public:
static const bool is_monotonic = true; // retained
static const bool is_steady = true;
};
typedef system_clock high_resolution_clock;
在GCC的情况下,你可以检查,如果你处理稳定时钟只需通过检查is_steady
和相应的行为。 然而VS2012似乎这里骗一点:-)
如果您需要高精度时钟,我建议现在写你自己的时钟符合C ++ 11的官方时钟接口,等待实现赶超。 它会比直接在代码中使用OS特定的API更好的方法。 对于Windows,你可以做这样的:
// Self-made Windows QueryPerformanceCounter based C++11 API compatible clock
struct qpc_clock {
typedef std::chrono::nanoseconds duration; // nanoseconds resolution
typedef duration::rep rep;
typedef duration::period period;
typedef std::chrono::time_point<qpc_clock, duration> time_point;
static bool is_steady; // = true
static time_point now()
{
if(!is_inited) {
init();
is_inited = true;
}
LARGE_INTEGER counter;
QueryPerformanceCounter(&counter);
return time_point(duration(static_cast<rep>((double)counter.QuadPart / frequency.QuadPart *
period::den / period::num)));
}
private:
static bool is_inited; // = false
static LARGE_INTEGER frequency;
static void init()
{
if(QueryPerformanceFrequency(&frequency) == 0)
throw std::logic_error("QueryPerformanceCounter not supported: " + std::to_string(GetLastError()));
}
};
对于Linux是,更容易。 只要阅读的手册页clock_gettime
和修改上面的代码。
GCC 5.3.0实施
C ++ STDLIB是GCC源内:
high_resolution_clock
是一个别名system_clock
system_clock
转发到第一个可用的以下内容: clock_gettime(CLOCK_REALTIME, ...)
gettimeofday
time
steady_clock
转发到第一个可用的以下内容: clock_gettime(CLOCK_MONOTONIC, ...)
system_clock
然后CLOCK_REALTIME
VS CLOCK_MONOTONIC
:在解释CLOCK_REALTIME和CLOCK_MONOTONIC之间的区别?