3

我想知道 QTimer 是否会在超时后继续计数。

例如,假设我有一个每 500 毫秒超时的 QTimer。假设当这个特定的 QTimer 超时时,我的程序恰好在我创建的某个函数中(不在事件循环中),并且程序从我的函数到事件循环需要 10 毫秒。这是否意味着下一次 QTimer 超时将在 1010 毫秒?

如果是这种情况,有没有办法绕过它?

谢谢。

编辑: 定时器结果

4

2 回答 2

2

当您放置一个带有 delay 的 Qtimer 时d,它会timeout()在这段时间过去之后触发一个信号,并且一旦窗口系统的事件队列中的所有事件都已处理完毕。

因此,如果您的程序花费任何时间不在事件循环中,那就没问题了。无论如何,无论是否在 Qt 中,将超时设置为t ms真正意味着,至少t ms在过去时唤醒我。你不能保证任何准确性。

ps:如果你担心很少ms,那么你应该担心时间粒度。

于 2012-04-04T12:17:01.507 回答
1

我使用多个计时器进行了一些测试,但使用了timerEvent( QObject::setTimer())。

问题是,当然,如果您有多个计时器在某个时间点干扰(恰好在同一时间滴答),您的所有doStuffThatTake10ms代码都将被“排队”......但是计时器的绝对精度应该随着时间的推移而保持不变。这里有一些代码来尝试一下。

#ifndef MULTITIMER_H
#define MULTITIMER_H

#include <QObject>
#include <QTime>

class MultiTimer : public QObject
{
    Q_OBJECT
public:
    explicit MultiTimer(QObject *parent = 0);
    void timerEvent(QTimerEvent *event);

private:
    int timerId[4];
    int interval[4];
    int count[4];
    QTime absoluteTimer;
};

#endif // MULTITIMER_H

实施.cpp

#include "MultiTimer.h"
#include <QTimerEvent>
#include <QTime>
#include <QDebug>

MultiTimer::MultiTimer(QObject *parent) :
    QObject(parent)
{
    interval[0] = 500;
    interval[1] = 1000;
    interval[2] = 1500;
    interval[3] = 2000;

    for( int i = 0; i < 4; i++)
        timerId[i] = startTimer(interval[i]);

    for( int i = 0; i < 4; i++)
        count[i] = 0;

    absoluteTimer.start();
}

void MultiTimer::timerEvent(QTimerEvent *event)
{
    int id = -1;
    for( int i = 0; i < 4; i++){
        if( event->timerId() == timerId[i]){
            id = i;
            count[id]++;
            break;
        }
    }

    if( id != -1) {
        qDebug() << "timer" << id
                 << "interval" << interval[id]
                 << "count" << count[id]
                 << "total" << count[id]*interval[id]
                 << "reference" << absoluteTimer.elapsed();

        usleep(10000);
    }
}

试一试 create a = QApllication()and a MultiTimerobject and fire a.exec()

在 linux 上 1 分钟后的结果

timer 1 interval 1000 count 59 total 59000 reference 59010 
timer 0 interval 500 count 119 total 59500 reference 59500 
timer 0 interval 500 count 120 total 60000 reference 60000 
timer 1 interval 1000 count 60 total 60000 reference 60010 
timer 3 interval 2000 count 30 total 60000 reference 60021 
timer 2 interval 1500 count 40 total 60000 reference 60031 
timer 0 interval 500 count 121 total 60500 reference 60500 

正如您所看到的,第 121 个滴答声timer 0是正确的60500ms……但60000ms所有计时器都会发生碰撞,从而导致执行延迟。

于 2012-04-05T19:58:27.903 回答