QT并发机制

QT 提供了多种并发编程机制,使得开发者能够充分利用多核处理器优势,同时保持代码的可维护性和跨平台特性。以下是 QT 主要的并发机制:

1. QThread - 线程基础类

QThread 是 QT 中最基础的线程类,提供了创建和管理线程的能力。

复制代码
class WorkerThread : public QThread {
    void run() override {
        // 在这里执行耗时操作
        qDebug() << "Worker thread running";
    }
};

// 使用
WorkerThread *thread = new WorkerThread;
thread->start(); // 启动线程

2. 基于 QObject 的线程模型

更推荐的方式是将 QObject 移动到线程中:

复制代码
class Worker : public QObject {
    Q_OBJECT
public slots:
    void doWork() {
        // 执行耗时任务
        emit resultReady(result);
    }
signals:
    void resultReady(const QString &result);
};

// 使用
QThread *thread = new QThread;
Worker *worker = new Worker;
worker->moveToThread(thread);

connect(thread, &QThread::started, worker, &Worker::doWork);
connect(worker, &Worker::resultReady, [](const QString &result){
    // 处理结果
});

thread->start();

3. QtConcurrent - 高级并发API

QtConcurrent 提供了更高层次的并发编程接口:

复制代码
// 并行映射
QList<int> list = {1, 2, 3, 4, 5};
QFuture<void> future = QtConcurrent::map(list, [](int &x){
    x *= 2;
});
future.waitForFinished(); // 等待完成

// 并行过滤
QFuture<int> filtered = QtConcurrent::filtered(list, [](int x){
    return x > 5;
});

// 并行归约
int sum = QtConcurrent::blockingReduced(list, [](int &result, int x){
    result += x;
});

4. QThreadPool 和 QRunnable

对于任务队列模式:

复制代码
class Task : public QRunnable {
    void run() override {
        // 执行任务
    }
};

// 使用
Task *task = new Task;
QThreadPool::globalInstance()->start(task);

5. 线程同步机制

QT 提供了多种线程同步工具:

  • QMutex - 互斥锁

    复制代码
    QMutex mutex;
    mutex.lock();
    // 临界区代码
    mutex.unlock();
    
    // 或使用 QMutexLocker
    QMutexLocker locker(&mutex);
    // 临界区代码
  • QReadWriteLock - 读写锁

    cpp

    复制代码
    QReadWriteLock lock;
    lock.lockForRead();  // 多个读取
    lock.lockForWrite(); // 单个写入
  • QSemaphore - 信号量

    复制代码
    QSemaphore sem(5); // 5个资源
    sem.acquire(3);    // 获取3个
    sem.release(2);    // 释放2个
  • QWaitCondition - 条件变量

    复制代码
    QWaitCondition condition;
    QMutex mutex;
    
    // 等待线程
    mutex.lock();
    condition.wait(&mutex);
    mutex.unlock();
    
    // 唤醒线程
    condition.wakeOne(); // 或 wakeAll()

6. 线程间通信

  • 信号槽机制:QT 的自动连接方式默认是队列连接(Qt::QueuedConnection),可以安全地跨线程通信

  • QMetaObject::invokeMethod:跨线程调用方法

    复制代码
    QMetaObject::invokeMethod(object, "methodName",
                             Qt::QueuedConnection,
                             Q_ARG(QString, "param"));

7. 异步操作

  • QFutureQFutureWatcher 用于监控异步操作

    复制代码
    QFuture<int> future = QtConcurrent::run([](){
        return 42;
    });
    
    QFutureWatcher<int> *watcher = new QFutureWatcher<int>;
    connect(watcher, &QFutureWatcher<int>::finished, [](){
        qDebug() << "Done";
    });
    watcher->setFuture(future);

最佳实践

  1. 避免直接继承 QThread,推荐使用 moveToThread

  2. 主线程只用于 GUI 操作,耗时操作放在工作线程

  3. 使用信号槽进行线程间通信,避免直接共享数据

  4. 使用 QMutexLocker 等 RAII 类管理锁资源

  5. 考虑使用 QtConcurrent 简化并行算法实现

相关推荐
上去我就QWER2 小时前
Qt中如何获取系统版本信息
开发语言·qt
十五年专注C++开发11 小时前
Qt-Nice-Frameless-Window: 一个跨平台无边框窗口(Frameless Window)解决方案
开发语言·c++·qt
江公望12 小时前
装了新的QtCreator17,没有用Qt5.12自带的QtCreator4,导致QtCreator17无法找到Qt5.12帮助文档
qt·qml
ctgu9014 小时前
PyQt5(八):ui设置为可以手动随意拉伸功能
开发语言·qt·ui
进击的大海贼16 小时前
QT/C++ 消息定时管理器
开发语言·c++·qt
Lj2_jOker18 小时前
QT 给Qimage数据赋值,显示异常,像素对齐的坑
开发语言·前端·qt
孤独的追光者21 小时前
使用Qt Designer开发上位机
开发语言·python·qt
Molesidy1 天前
【随笔】【QT】QT5.15.2版本的最新下载方式!!!
开发语言·qt
梨轻巧1 天前
pyside6的历史发展、Qt 介绍、PyQt 和 pyside6对比
qt·pyqt
恋恋西风2 天前
Qt 打开文件列表选择文件,实现拖拽方式打开文件,拖拽加载
开发语言·qt