【发布时间】:2023-03-28 17:08:01
【问题描述】:
我正在使用系统计时器(clock() 函数,请参阅 time.h)对一些串行和 USB 通信进行计时。我只需要大约 1 毫秒的准确度。我注意到的第一件事是单个时间可以超出(正负)10 毫秒。随着事件的进行,对一些较小的事件进行计时会导致计时的准确性降低。总体时间稍好一些。在 MSDN 等上有点根之后,我偶然发现了 Windows 多媒体库中的计时器(timeGetTime(),参见 MMSystem.h)。这要好得多,准确度可以达到 1 毫秒。
随后发生了奇怪的事情,在最初完美无瑕地工作了几天之后(可爱的日志和有用的时间),这一切都变成了梨形,因为这个 API 也开始显示这种奇怪的粒度(而不是一堆小的通信消息需要 3 毫秒、2 毫秒、3 毫秒、2 毫秒, 3ms 等。它以 0ms、0ms、0ms、0ms、15ms 等出现。重新启动 PC 恢复正常精度,但在某个不确定的时间(大约一个小时后)异常返回。
任何人对如何在 Windows XP(32 位专业版,使用 Visual Studio 2008)上获得这种级别的计时精度有任何想法或建议。
我的小计时课:
class TMMTimer
{
public:
TMMTimer( unsigned long msec);
TMMTimer();
void Clear() { is_set = false; }
void Set( unsigned long msec=0);
bool Expired();
unsigned long Elapsed();
private:
unsigned long when;
int roll_over;
bool is_set;
};
/** Main constructor.
*/
TMMTimer::TMMTimer()
{
is_set = false;
}
/** Main constructor.
*/
TMMTimer::TMMTimer( unsigned long msec)
{
Set( msec);
}
/** Set the timer.
*
* @note This sets the timer to some point in the future.
* Because the timer can wrap around the function sets a
* rollover flag for this condition which is checked by the
* Expired member function.
*/
void TMMTimer::Set( unsigned long msec /*=0*/)
{
unsigned long now = timeGetTime(); // System millisecond counter.
when = now + msec;
if (when < now)
roll_over = 1;
else
roll_over = 0;
is_set = true;
}
/** Check if timer expired.
*
* @return Returns true if expired, else false.
*
* @note Also returns true if timer was never set. Note that this
* function can handle the situation when the system timer
* rolls over (approx every 47.9 days).
*/
bool TMMTimer::Expired()
{
if (!is_set)
return true;
unsigned long now = timeGetTime(); // System millisecond counter.
if (now > when)
{
if (!roll_over)
{
is_set = false;
return true;
}
}
else
{
if (roll_over)
roll_over = false;
}
return false;
}
/** Returns time elapsed since timer expired.
*
* @return Time in milliseconds, 0 if timer was never set.
*/
unsigned long TMMTimer::Elapsed()
{
if (!is_set)
return 0;
return timeGetTime()-when;
}
【问题讨论】:
-
谢谢大家,这似乎是我需要的。