QT5跨线程通信,没有调用插槽"这个"上下文

时间:2016-05-04 12:59:42

标签: multithreading qt signals-slots queued-connection

由于moveToThread方法,我有一个对象 MainWorker 作为单独的线程运行。 MainWorker 有一个 SubWorker 成员,该成员也作为单独的线程运行。两个线程都在无限循环中工作。

这个想法是, MainWorker SubWorker 都执行一些单独的计算。每当 SubWorker 完成计算时,它应该通知结果 MainWorker

因此,我直观地将 SubWorker 发出的信号与 MainWorker 的插槽之间建立了第一个连接,但它不起作用,所以我再建两个连接排除一些潜在的问题:

connect(subWorker, &SubWorker::stuffDid, this, &MainWorker::reportStuff)); //1
connect(subWorker, &SubWorker::stuffDid, subWorker, &SubWorker::reportStuff); //2
connect(this, &MainWorker::stuffDid, this, &MainWorker::reportStuffSelf); //3

看来,不起作用的正是我所需要的 - 跨线程通信,因为连接2和3按预期工作。我的问题是:如何使连接1工作?

编辑:显然,在Karsten的解释之后,很明显无限循环会阻止EventLoop。所以新的问题是,如何从无限循环线程向其父线程发送消息(信号,无论如何)?

我是Qt的新手,我很有可能完全错了。这里是最小的(不是)工作示例:

MainWorker.h

class MainWorker : public QObject
{
Q_OBJECT

public:
    MainWorker() : run(false) {}

void doStuff()
{
    subWorker = new SubWorker;
    subWorkerThread = new QThread;
    subWorker->moveToThread(subWorkerThread);
    connect(subWorkerThread, &QThread::started, subWorker, &SubWorker::doStuff);
    if(!connect(subWorker, &SubWorker::stuffDid, this, &MainWorker::reportStuff)) qDebug() << "connect failed";
    connect(subWorker, &SubWorker::stuffDid, subWorker, &SubWorker::reportStuff);
    connect(this, &MainWorker::stuffDid, this, &MainWorker::reportStuffSelf);

    subWorkerThread->start();

    run = true;
    while(run)
    {
        QThread::currentThread()->msleep(200);
        emit stuffDid();
    }
}

private:
    bool run;
    QThread* subWorkerThread;
    SubWorker* subWorker;

signals:
    void stuffDid();

public slots:
    void reportStuff()
    {
        qDebug() << "MainWorker: SubWorker did stuff";
    }

    void reportStuffSelf()
    {
        qDebug() << "MainWorker: MainWorker did stuff (EventLoop is not blocked)";
    } 
};

SubWorker.h

class SubWorker : public QObject
{
    Q_OBJECT

public:
    SubWorker() : run(false) {}

    void doStuff()
    {
        run = true;
        while(run)
        {
            qDebug() << "SubWorker: Doing stuff...";
            QThread::currentThread()->msleep(1000);
            emit stuffDid();
        }
    }

private:
    bool run;

public slots:
    void reportStuff()
    {
        qDebug() << "SubWorker: SubWorker did stuff";
    }

signals:
    void stuffDid();
};

的main.cpp

int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);

    MainWorker *mainWorker = new MainWorker;
    QThread *mainWorkerThread = new QThread;
    mainWorker->moveToThread(mainWorkerThread);
    QObject::connect(mainWorkerThread, &QThread::started, mainWorker, &MainWorker::doStuff);
    mainWorkerThread->start();

    return a.exec();
}

0 个答案:

没有答案