簡體   English   中英

QTimer未在線程中觸發

[英]QTimer not firing in a thread

我有一個帶有2個線程的Qt5 c ++應用程序,主程序啟動時啟動了線程A。 線程A的啟動方法成功運行。

到現在為止還挺好。 接下來,在主程序中,我向線程A發送一個信號以啟動QTimer,它確實可以-但是該計時器永不過期!

線程B處理tcp連接。 當我啟動與應用程序的telnet連接時,線程B啟動,突然我看到線程A的Qtimer以正常間隔過期。

為什么直到線程B啟動,線程A的QTimer才到期?

我懷疑我的線程弄亂了。 請注意下面的代碼的最后一部分,該產品是:

thread of this:  QThread(0x200fe00)  
thread of timer:  QThread(0x1fff470)

這表明我的工作程序對象(this)與計時器對象處於不同的線程中。 此計時器線程地址實際上是MAIN線程。 為什么? 我糊塗了。

有什么建議嗎?


在我的主應用程序中,我這樣創建並啟動線程:

QThread * MyControllerThread = new QThread(this);

if (MyControllerThread) {

    TheController *worker = new TheController(MyControllerThread);

    if (worker) {
        connect(MyControllerThread, SIGNAL(started()), worker, SLOT(start()));
        connect(MyControllerThread, SIGNAL(finished()), worker, SLOT(deleteLater()));
        connect(MyControllerThread, SIGNAL(finished()), MyControllerThread, SLOT(deleteLater()));
        worker->moveToThread(MyControllerThread);  
        MyControllerThread->start();  
    } 

在主應用程序中,我向新線程發出信號:

    emit sig_startlocalpeer(Types::EActionLocalServiceStart);  // Move the local peer to standby mode to start remote tests

它在我的線程(TheController對象)中運行一個插槽:

connect(&m_remotetestintervaltimer,SIGNAL(timeout()),this,SLOT(expiredRemoteTestIntervalTimer()));
m_remotetestintervaltimer.setTimerType(Qt::VeryCoarseTimer);
m_remotetestintervaltimer.start(REMOTETEST_TIMER_INTERVAL);  // Wait between ticks
qDebug() << "thread of this: " << this->thread();
qDebug() << "thread of timer: " << m_remotetestintervaltimer.thread();

好吧,這不是Qt5的錯誤,而是對Qt的線程精神的不准確的了解。

在Qt中,有兩種實現線程的方法,它們使用的是偶數循環,也可以不使用偶數循環。 這只是一個小的視覺示例。

沒有事件循環

myMethodCalledInANewThread
{
    do{ ... }while(...);
}

具有事件循環

myMethodCalledInANewThread
{
    [...]
    exec();
}

(當然,您可以將一個do / while與一個偶數循環混合在一起,但保持簡單)。

在QTimer的文檔中,您可以閱讀:

在多線程應用程序中,可以在具有事件循環的任何線程中使用QTimer。 [...] Qt使用計時器的線程關聯性來確定哪個線程將發出timeout()信號。 因此,您必須在其線程中啟動和停止計時器。 無法從另一個線程啟動計時器。

因此,我非常確定您在第二個線程中沒有第二個事件循環,這就是您具有所描述的行為的原因。

為了給您一些使用Qt完全清楚了解線程的提示,建議您閱讀以下內容:

一篇非常好的文章,介紹了許多用戶如何誤解QThread實現。 -您做錯了: http : //blog.qt.digia.com/blog/2010/06/17/youre-doing-it-wrong/

我希望它會有所幫助;)

最好的答案似乎是RobbieE和Kuba的結合:

您必須在構造函數中顯式設置成員變量的父級。 父子功能是Qt事物,它存在於從QObject派生的類中,而不是C ++的功能。

我從來不知道這一點-我假設創建對象時,其成員變量會自動將其父對象設置為該對象。 很高興知道!!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM