QThread子类run方法内调用的函数运行在哪个线程?
核心结论
你示例中run()内部调用的noMemberFunc()和memberFunc()全部运行在QThread启动的新子线程中,不会阻塞主线程。
原理说明
QThread本身是线程管理类,它的实例依附于创建它的线程(你这里就是主线程),这也是你之前理解的“除run外的方法归属旧线程”的正确场景:如果你主动在主线程调用helperThread实例->memberFunc(),这个调用才会执行在主线程。
而QThread::start()被调用后,操作系统会创建一个全新的工作线程,这个工作线程的执行入口就是run()函数,run()执行路径下所有直接、间接调用的函数,不管是全局函数、类成员函数还是lambda,全部运行在这个工作线程中,和主线程完全独立,不会阻塞主线程。
线程验证方法
Qt提供了直接获取当前线程标识的接口:QThread::currentThreadId(),你可以在任意位置打印线程ID对比即可,示例代码如下:
#include <QDebug> #include <QThread> // 主线程中打印 qDebug() << "主线程ID:" << QThread::currentThreadId(); // 在noMemberFunc、memberFunc、run中分别添加打印 qDebug() << "当前函数运行线程ID:" << QThread::currentThreadId();
打印后你会发现run()以及它调用的两个函数的线程ID完全一致,且和主线程ID不同。
补充说明
你手上子类化QThread的旧项目能正常运行是完全合理的,官方不推荐子类化只是因为moveToThread的方案能更好的把业务逻辑和线程管理解耦,灵活性更高,并不是子类化QThread的写法本身有错误。
内容的提问来源于stack exchange,提问作者Charles Tucker 3
相关产品推荐
相关产品推荐

