《QThread源码浅析》
《子类化QThread实现多线程》
《子类化QObject+moveToThread实现多线程》
《继承QRunnable+QThreadPool实现多线程》
本文章实例的源码地址:https://gitee.com/CogenCG/QThreadExample.git
在QT开发的场景中,个人觉得此方法使用的也比较少,所以本文只作一个简单使用的介绍。QtConcurrent 是命名空间 (namespace),它提供了高层次的函数接口 (APIs),使所写程序,可根据计算机的 CPU 核数,自动调整运行的线程数目。本文以 Qt 中的 QtConcurrent::run() 函数为例,介绍如何将函数运行在单独的线程中。
(1)使用 QtConcurrent 模块,需要在 .pro 中添加:
QT += concurrent(2)将一个普通函数运行在单独线程:
#include <QApplication> #include <QDebug> #include <QThread> #include <QtConcurrent> void fun1(){ qDebug()<<__FUNCTION__<<QThread::currentThread(); } void fun2(QString str1, QString str2){ qDebug()<<__FUNCTION__<<str1+str2<<QThread::currentThread(); } int fun3(int i, int j){ qDebug()<<__FUNCTION__<<QThread::currentThread(); return i+j; } int main(int argc, char *argv[]) { QApplication a(argc, argv); qDebug()<<__FUNCTION__<<QThread::currentThread(); //无参数的普通函数 QFuture<void> fut1 = QtConcurrent::run(fun1); //有参数的普通函数 QFuture<void> fut2 = QtConcurrent::run(fun2, QString("Thread"),QString(" 2")); //获取普通函数的返回值 int i=1, j=2; QFuture<int> fut3 = QtConcurrent::run(fun3, i, j); qDebug()<<"ret:"<<fut3.result(); //以上的例子,如果要为其指定线程池,可以将线程池的指针作为第一个参数传递进去 QThreadPool pool; QFuture<void> fut4 = QtConcurrent::run(&pool, fun1); fut1.waitForFinished(); fut2.waitForFinished(); fut3.waitForFinished(); fut4.waitForFinished(); return a.exec(); }输出结果:
qMain QThread(0xf380590) fun2 "Thread 2" QThread(0x1ca7c758, name = "Thread (pooled)") fun1 QThread(0x1ca7c6d8, name = "Thread (pooled)") fun3 QThread(0x1ca7c5b8, name = "Thread (pooled)") ret: 3 fun1 QThread(0x1ca7c438, name = "Thread (pooled)")(3)将类中的成员函数单独运行在线程中:
将类中的成员函数运行在某一个线程中,可将指向该类实例的引用或指针作为 QtConcurrent::run 的第一个参数传递进去,常量成员函数一般传递常量引用 (const reference),而非常量成员函数一般传递指针 (pointer)。
常量成员函数
在一个单独的线程中,调用 QByteArray 的常量成员函数 split(),传递给 run() 函数的参数是 bytearray
//常量成员函数QByteArray::split() QByteArray bytearray = "hello,world"; QFuture<QList<QByteArray> > future = QtConcurrent::run(bytearray, &QByteArray::split, ','); QList<QByteArray> result = future.result(); qDebug()<<"result:"<<result;非常量成员函数
在一个单独的线程中,调用 QImage 的非常量成员函数 invertPixels(),传递给 run() 函数的参数是 &image
QImage image = ...; QFuture<void> future = QtConcurrent::run(&image, &QImage::invertPixels, QImage::InvertRgba); ... future.waitForFinished(); // At this point, the pixels in 'image' have been inverted