QT之处理密集响应时的保持(界面操作无反应)
前因:如果处理一个特定任务上耗费的时间过多时,那么用户界面就会变得无法响应。
解决方案:
重点:多线程
一. 使用processEvents()函数来保持用户界面的响应-----在代码中频繁调用该函数即可QApplication::processEvents()。这个函数告诉QT处理所有那些还没有被处理的各类事件,然后将控制权返回给调用者。
使用这个方法的时候存在一个潜在的问题:应用程序还在执行的时候,就关闭了主窗口或者点击了其他响应,会产生预料不到的后果。解决方案:替换成QApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
二. 使用多线程
方式一:继承QThread重写虚函数run().
示例:
.h
.cpp run函数里面放自己需要耗时的操作
调用,如此便开启了一个线程
SendMsgThread *smt = new SendMsgThread(); smt->start();
注:如果需要删除一个存在于不同线程中的QObject对象,则必须调用线程安全的**QOBject::deleteLater()**函数,它可以置入一个延期删除时间.
方式二:void QObject::moveToThread ( QThread * targetThread )子类化QObject,利用信号和槽进行关联
1.定义一个继承QObject的类A;
2.在类A里定义一个槽函数slot();
3.QThread *thread = new QThread();将类A的实例的对象a调用moveToThread(thread);
4.绑定信号槽connect(thread, &QThread::started, a,&A::slot());//绑定线程的开始信号,线程开始后就会执行类A的槽函数
5.启动线程thread.start()。
具体使用方法以及如何利用moveToThread创建多线程的方法可以看这篇博客
QT 多线程 之MoveToThread使用详解
方式三:并发模块:QtConCurrent::run()
QtConcurrent这是一个高级 API,构建于QThreadPool之上,它提供更高层次的函数接口(APIs),使所写的程序,可根据计算机的CPU核数,自动调整运行的线程数量.
主要功能是令启动一个线程来执行一个函数.
注意,QtConcurrent是一个命名空间而不是一个类,因此其中的所有函数都是命名空间内的全局函数。
使用时要添加:
pro文件:QT += concurrent
头文件:
使用方法:
QtConcurrent::run()可以开辟一个单独的线程来运行我们定义的函数(可以在里面执行一些耗时或者需要并行的计算),QtConcurrent::run()返回一个QFuture模板类,用来处理函数的返回值。
QFuture future;//可以获得计算的结果值
future.waitForFinished();等待线程结束,实现阻塞。
future. isFinished() 判断线程是否结束
future.isRunning() 判断线程是否在运行
future.result() 取出线程函数的返回值
1 全局函数或静态函 ,作为线程函数------------线程执行不带参数
QFuture QtConcurrent::run(Function function, …),例:
2 线程执行类成员函数(带参数):run的第一个参数必须是const引用或者对象指针
3 结构体函数作为线程函数
sturct worker
{
int ID;
void worker::threadFunc()
{ }
};
worker work;
QtConcurrent::run(&work,&worker::threadFunc);
使用示例:
新人创作打卡挑战赛 发博客就能抽奖!定制产品红包拿不停!