Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/qt/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何在qt中从另一个线程运行qt并发时关闭程序_C++_Qt_Qthread_Qtconcurrent - Fatal编程技术网

C++ 如何在qt中从另一个线程运行qt并发时关闭程序

C++ 如何在qt中从另一个线程运行qt并发时关闭程序,c++,qt,qthread,qtconcurrent,C++,Qt,Qthread,Qtconcurrent,我正在运行一个具有多线程的程序。程序首先有一个主/UI线程在其中运行。在这个程序中,我有一个worker和handler类 工人类有一个模拟函数,它只生成随机数。simulate函数在不阻塞任何线程的情况下(即通过Qtconcurrent)连续生成数字 从main/UI线程,我将这个worker类放入新线程。handler类运行在main/UI线程中,负责通过信号槽与其他线程中运行的worker类通信 目前一切正常。 当我试图通过点击应用程序的交叉按钮来关闭程序时,问题就开始了最新版本 程序挂起

我正在运行一个具有多线程的程序。程序首先有一个主/UI线程在其中运行。在这个程序中,我有一个worker和handler类

工人类有一个模拟函数,它只生成随机数。simulate函数在不阻塞任何线程的情况下(即通过Qtconcurrent)连续生成数字

从main/UI线程,我将这个worker类放入新线程。handler类运行在main/UI线程中,负责通过信号槽与其他线程中运行的worker类通信

目前一切正常。

当我试图通过点击应用程序的交叉按钮来关闭程序时,问题就开始了最新版本 程序挂起但不关闭。但是,当我不将worker放在另一个类中并从同一个主/UI线程运行worker类时,就没有问题了,程序将以0退出

所以我的问题是如何停止另一个线程,并最终关闭另一个线程

多谢各位

main.cpp

int main(int argc, char *argv[])
{
    QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);

    QGuiApplication app(argc, argv);

    QQmlApplicationEngine engine;

    QThread l_newThread;

    Worker* l_worker = new Worker();
    handler * l_handler = new handler();

    l_worker->moveToThread(&l_newThread);

    QObject::connect(&l_newThread, &QThread::started, l_worker, &Worker::Init);

    QObject::connect(l_handler,&handler::toStop_Signal,&l_newThread, &QThread::quit);
    QObject::connect(l_worker, &Worker::toStop_Signal_Worker, l_handler,&handler::toStop_Slot);
    QObject::connect(&app,&QCoreApplication::aboutToQuit, l_worker, &Worker::stop);
   // QObject::connect(&app,&QCoreApplication::aboutToQuit, &l_newThread, &QThread::quit);

    l_newThread.start();
   // l_worker->Init();

    engine.load(QUrl(QStringLiteral("qrc:/main.qml")));

    if (engine.rootObjects().isEmpty())
        return -1;

    int result = app.exec();

    l_newThread.wait();

    return result;
}
worker.cpp

#include "worker.h"

Worker::Worker(QObject *parent) : QObject(parent)
{

}

void Worker:: Init()
{
    m_simulation = true;
    simulate();
}

void Worker::simulate()
{
    QtConcurrent::run([this]{
        QRandomGenerator generator;

        while (m_simulation) {


            qint32 t = generator.bounded(0,100);
            qDebug() << t;


            qDebug() << "sleeping for 1 second";
            QThread::sleep(1);
        }

        if (!m_simulation) {
            qDebug() << "Killing the concurrent thread";
            //  QThread::currentThread()->exit();
            emit toStop_Signal_Worker();
        }
    });

}

void Worker::stop()
{
    m_simulation = false;
}
结果


这里可能发生的情况是:用于退出新线程的信号
toStop\u signal
从未被传递,因为当它被发出时,事件循环已经死了。因此,您的程序在等待
l_newThread.wait()中的线程时被卡住了

我完全不明白为什么要启动这个线程,只是为了在后面使用
QtConcurrent::run
,然后再跨另一个线程

无论如何,一旦您确定您的工作线程已经停止(并且根据您发布的输出,您已经停止),您就可以安全地直接在
main
中退出(基本上无用的)线程:

int result = app.exec();

l_newThread.exit(); //just quit it
l_newThread.wait();

return result;
然后您可以摆脱此连接:

QObject::connect(l_handler,&handler::toStop_Signal,&l_newThread, &QThread::quit);

(我猜)还有处理程序。

谢谢,这次我试了一下,它没有停止处理程序,因为它一直在运行。如何确保先停止qt并发,然后停止/退出另一个线程。
int result = app.exec();

l_newThread.exit(); //just quit it
l_newThread.wait();

return result;
QObject::connect(l_handler,&handler::toStop_Signal,&l_newThread, &QThread::quit);