主线程代码:点击创建线程时创建线程,点击执行时将数据发送到后台线程处理,处理完成后发送回主线程:
#include "MainWindow.h"
#include "ui_MainWindow.h"
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow)
{
ui->setupUi(this);
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId();
thread1_ = 0;
thread2_ = 0;
number_ = 0;
}
MainWindow::~MainWindow()
{
delete ui;
}
void MainWindow::ProcessComplete(Qt::HANDLE threadId, int num)
{
qDebug()<<__PRETTY_FUNCTION__<<threadId<<num<<"complete";
}
void MainWindow::on_btn_start_1__clicked()
{
if(!thread1_)
{
thread1_ = new MyThread1();
connect(thread1_,SIGNAL(ProcessComplete(Qt::HANDLE,int)),this,SLOT(ProcessComplete(Qt::HANDLE,int)));
connect(this,SIGNAL(Process(int)),thread1_,SLOT(Process(int)));
thread1_->start();
}
}
void MainWindow::on_btn_start_2__clicked()
{
if(!thread2_)
{
thread2_ = new QThread();
MyThread2 * th2 = new MyThread2();
connect(th2,SIGNAL(ProcessComplete2(Qt::HANDLE,int)),this,SLOT(ProcessComplete(Qt::HANDLE,int)));
connect(this,SIGNAL(Process2(int)),th2,SLOT(Process2(int)));
th2->moveToThread(thread2_);
thread2_->start();
}
}
void MainWindow::on_btn_process_1__clicked()
{
++number_;
if(thread1_)
emit Process(number_);
}
void MainWindow::on_btn_process_2__clicked()
{
++number_;
if(thread2_)
emit Process2(number_);
}
方式一:继承自QThread,重写run,run中执行的代码为子线程代码,但是注意run与其他函数不在一个线程,如对象的槽函数与run不在一个线程,使用需要注意线程同步问题。使用时实例化后start就可以了
#include "MyThread1.h"
MyThread1::MyThread1()
{
}
void MyThread1::Process(int num)
{
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"recv"<<num;
mutex_.lock(); //这里要加锁,,,,
list_.push_back(num);
mutex_.unlock();
condition_.wakeAll();
}
void MyThread1::run()
{
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"in";
while (true)
{
wait_.lock();
condition_.wait(&wait_,5000);
wait_.unlock();
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"waited";
while(list_.size() > 0)
{
mutex_.lock();
int num = list_.front();
list_.pop_front();
mutex_.unlock();
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"process"<<num;
msleep(3000);//耗时
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"process complete"<<num;
emit ProcessComplete(QThread::currentThreadId(),num);
}
}
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"out";
}
使用代码:
thread1_ = new MyThread1();
connect(thread1_,SIGNAL(ProcessComplete(Qt::HANDLE,int)),this,SLOT(ProcessComplete(Qt::HANDLE,int)));
connect(this,SIGNAL(Process(int)),thread1_,SLOT(Process(int)));
thread1_->start();
效果:
方法二:继承自QObject,使用时使用QObject::moveToThread即可,这时候对象的所有函数都在子线程运行,不需要加锁,使用比较方便:
#include "MyThread2.h"
MyThread2::MyThread2(QObject *parent) : QObject(parent)
{
}
void MyThread2::Process2(int num)
{
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"process"<<num;
QThread::msleep(3000);//耗时
qDebug()<<__PRETTY_FUNCTION__<<QThread::currentThreadId()<<"processed"<<num;
emit ProcessComplete2(QThread::currentThreadId(),num);
}
使用代码:
thread2_ = new QThread();
MyThread2 * th2 = new MyThread2();
connect(th2,SIGNAL(ProcessComplete2(Qt::HANDLE,int)),this,SLOT(ProcessComplete(Qt::HANDLE,int)));
connect(this,SIGNAL(Process2(int)),th2,SLOT(Process2(int)));
th2->moveToThread(thread2_);
thread2_->start();
效果:
两种方式对比:
方式一使用比较麻烦,但是他可以缓冲数据,比如你快速的发送一堆数据到子线程后,可以放到链表中缓存,然后子线程慢慢处理,但是需要处理多线程问题,而且往往需要使用一个while循环去检测和处理
方式二使用简单,但是你发送出去的数据,对子线程来说,必然是按照顺序到达和处理的
代码链接:https://github.com/yangyang0312/QtTestCode/tree/master/QtThread
今天的文章QThread使用分享到此就结束了,感谢您的阅读。
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
如需转载请保留出处:https://bianchenghao.cn/9054.html