gpt4 book ai didi

c++ - 如何在 Qt 中重新启动一个线程?

转载 作者:行者123 更新时间:2023-11-30 02:46:29 25 4
gpt4 key购买 nike

我正在使用一个单独的线程进行串行端口通信。这个线程应该在我们想要连接串行端口时启动,并在出现错误/断开连接时结束。

问题是如果线程已经完成一次,下次我们想要重新连接时它不会重新启动。

SerialIO::SerialIO(SettingsDialog *settings) :  //Worker. Extends QObject
settings(settings)
{
serial = new QSerialPort(this);
}

SerialIO::~SerialIO()
{
serial->close();
//something else?
}


/* PUBLIC SLOT */
void SerialIO::connectSP()
{
/* connects with some port, if not succesfull, emits an error signal */
}

MainWindow::MainWindow(QWidget *parent)
: QWidget(parent)
{
//...
serialio = new SerialIO(settings);
serialio->moveToThread(&thread);

QObject::connect(&thread,SIGNAL(started()),serialio,SLOT(connectSP()));
QObject::connect(&thread,SIGNAL(finished()),serialio,SLOT(deleteLater()));
QObject::connect(serialio,SIGNAL(error(const QString)),this,SLOT(handleError(const QString&)));
//...

}

void MainWindow::connect()
{
if(!thread.isRunning()){
thread.start();
}

}

void MainWindow::handleError(const QString &msg){
QMessageBox::information(this, "Error", msg);
if(thread.isRunning()){
thread.quit();
thread.wait();
}
}

似乎线程没有正常结束,但我已经检查过线程没有运行!然后程序意外结束。


解决方法:

QObject::connect(&thread,SIGNAL(started()),serialio,SLOT(connectSP()));
QObject::connect(&thread,SIGNAL(finished()),serialio,SLOT(disconnectSP()));
QObject::connect(serialio,SIGNAL(bye()),&thread,SLOT(quit()));

最佳答案

deleteLater() 将事件发布到事件队列(如重绘事件、计时器事件或网络事件)。如果事件得到处理,它会删除该对象。如果没有事件循环,则您的对象不会被删除。

您首先退出线程,这会导致您的对象未被检测到,因此您的析构函数不会被调用。

您应该将线程的 finished() 信号连接到一个插槽以断开连接:

QObject::connect(&thread,SIGNAL(finished()),serialio,SLOT(disconnectSP())); 

void SerialIO::disconnectSP()
{
serial->close();
}

此外,也无需调用 deleteLater(),因为您只更新了一次对象。

关于c++ - 如何在 Qt 中重新启动一个线程?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23535204/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com