《Qt 实验分析教程》 – 第 83 课勘误
在 Qt 中通过组合的方法实现多线程类是一种常用的设计模式,其原理是直接
响应 started() 信号,在子线程中执行指定的线程体函数(tmain() 槽函数)。
AnotherThread::AnotherThread(QObject *parent) :
QObject(parent)
{
moveToThread(&m_thread);
connect(&m_thread, SIGNAL(started()), this, SLOT(tmain()));
}
在 Qt4 之后,QThread::run() 函数中默认调用了 QThread::exec() 函数;因
此,tmain() 函数(线程体函数)执行结束后会直接进入事件循环,导致线程永远
无法自动结束。解决该问题的方法是,在 tmain() 函数的最后调用
QThread::quit() 函数,主动结束线程的事件循环。
void AnotherThread::tmain()
{
/* thread entry body */
m_thread.quit(); // IMPORTANT !!!
}
视频中,由于疏忽大意,在编写 tmain() 函数的时候忘了调用
QThread::quit() 函数,导致线程对象无法销毁。
#include <QtCore/QCoreApplication>
#include <QDebug>
#include <QThread>
#include "AnotherThread.h"
void test()
{
AnotherThread at;
at.start();
}
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
qDebug() << "main() tid = " << QThread::currentThreadId();
test();
return a.exec();
}
#ifndef ANOTHERTHREAD_H
#define ANOTHERTHREAD_H
#include <QObject>
#include <QThread>
class AnotherThread : public QObject
{
Q_OBJECT
QThread m_thread;
protected slots:
void tmain();
public:
explicit AnotherThread(QObject *parent = 0);
void start();
void terminate();
void exit(int c);
~AnotherThread();
};
#endif // ANOTHERTHREAD_H
#include "AnotherThread.h"
#include <QDebug>
AnotherThread::AnotherThread(QObject *parent) :
QObject(parent)
{
moveToThread(&m_thread);
connect(&m_thread, SIGNAL(started()), this, SLOT(tmain()));
}
void AnotherThread::tmain()
{
qDebug() << "void AnotherThread::tmain() tid = " << QThread::currentThreadId();
for(int i=0; i<10; i++)
{
qDebug() << "void AnotherThread::tmain() i = " << i;
}
qDebug() << "void AnotherThread::tmain() end";
m_thread.quit();
}
void AnotherThread::start()
{
m_thread.start();
}
void AnotherThread::terminate()
{
m_thread.terminate();
}
void AnotherThread::exit(int c)
{
m_thread.exit(c);
}
AnotherThread::~AnotherThread()
{
m_thread.wait();
}