繁体   English   中英

QTimer的方法'isActive()'是线程安全的吗?

[英]Is the method 'isActive()' of QTimer threadsafe?

我目前正在考虑QTimer实现的线程安全性。

在我的应用程序中,我使用bool isActive()方法检查计时器是否正在运行。 当我计划在其他线程中也使用此方法时,我的想法就涉及线程安全性考虑因素。

根据我的研究, bool isActive()方法不是线程安全的。

这是我的假设:

QTimer的实现( QTimer源代码 )显示, bool isActive()仅检查成员变量int id; 大于0:

inline bool isActive() const { return id >= 0; }

此成员变量在构造函数中使用INV_TIMER初始化, INV_TIMER-1的定义。 当计时器启动时,它将被设置为int QObject::startTimer(int interval)的返回值。

/*! \overload start()
    Starts or restarts the timer with the timeout specified in \l interval.
    If \l singleShot is true, the timer will be activated only once.
*/
void QTimer::start()
{
    if (id != INV_TIMER)                        // stop running timer
        stop();
    nulltimer = (!inter && single);
    id = QObject::startTimer(inter);
}

当我从另一个线程在QTimer::start()期间执行对isActive()的调用时,我认为bool isActive()的返回值可能无效。

我会感谢能够验证我的假设的人的意见。

为了达到线程安全,我只需使用互斥体将对计时器的调用包装起来,如下面的代码片段所示。

class SensorControl : public QObject
{
    Q_OBJECT

public:
    SensorControl();    // inits and interval-settings are done at implementation

    bool Start()
    {
        QMutexLocker lock(&m_mutexTimer);
        return m_pTimer->start();
    }

    void Stop()
    {
        QMutexLocker lock(&m_mutexTimer);
        return m_pTimer->stop();
    }

    bool IsMeasuring() const
    {
        QMutexLocker lock(&m_mutexTimer);
        return m_pTimer->isActive();
    }

private:

    QMutex m_mutexTimer;
    QTimer* m_pTimer;

};

如果你想调用QTimer::isActive从另一个线程,那么你的解决方案看起来是安全的。 isActive只访问id成员变量,因此您需要互斥保护所有对id写入以及从线程中读取id 您是为isActivestop这样做的,所以看起来不错。

请注意,如果您曾经调用其他写入idQTimer方法,则将获得未定义的行为。 因此,请注意不要调用诸如QTimer::setInterval()QTimer::~QTimer() (!)之类的东西。 也不要使用Singleshot计时器,因为它将写入QTimer::timerEvent() id

通常,包装一个现有的类并添加互斥体是危险的,这是否起作用取决于该类的内部,并且很难在所有情况下进行检查。 同样,内部结构可能在下一个Qt版本中发生变化,也许在下一个版本中QTimer::timerEvent()将无条件地更改id ,并且您的解决方案不再是线程安全的。

因此,尽管您的方法可行,但总体上我还是建议不要这样做。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM