QThread 类

QThread 类提供独立于平台的方式去管理线程。 更多...

头: #include <QThread>
qmake: QT += core
继承: QObject

公共类型

enum Priority { IdlePriority, LowestPriority, LowPriority, NormalPriority, ..., InheritPriority }

公共函数

QThread (QObject * parent = Q_NULLPTR)
~QThread ()
QAbstractEventDispatcher * eventDispatcher () const
void exit (int returnCode = 0)
bool isFinished () const
bool isInterruptionRequested () const
bool isRunning () const
int loopLevel () const
优先级 priority () const
void requestInterruption ()
void setEventDispatcher (QAbstractEventDispatcher * eventDispatcher )
void setPriority (Priority priority )
void setStackSize (uint stackSize )
uint stackSize () const
bool wait (unsigned long time = ULONG_MAX)

重实现公共函数

virtual bool event (QEvent * event )

公共槽

void quit ()
void start (Priority priority = InheritPriority)
void terminate ()

信号

void finished ()
void started ()

静态公共成员

QThread * currentThread ()
Qt::HANDLE currentThreadId ()
int idealThreadCount ()
void msleep (unsigned long msecs )
void sleep (unsigned long secs )
void usleep (unsigned long usecs )
void yieldCurrentThread ()

保护函数

int exec ()
virtual void run ()

静态保护成员

void setTerminationEnabled (bool enabled = true)

额外继承成员

详细描述

QThread 类提供独立于平台的方式去管理线程。

A QThread object manages one thread of control within the program. QThreads begin executing in run ()。默认情况下, run () 启动事件循环通过调用 exec () 并在线程内运行 Qt 事件循环。

可以使用 Worker 对象,通过把它们移动到线程使用 QObject::moveToThread ().

class Worker : public QObject
{
    Q_OBJECT
public slots:
    void doWork(const QString &parameter) {
        QString result;
        /* ... here is the expensive or blocking operation ... */
        emit resultReady(result);
    }
signals:
    void resultReady(const QString &result);
};
class Controller : public QObject
{
    Q_OBJECT
    QThread workerThread;
public:
    Controller() {
        Worker *worker = new Worker;
        worker->moveToThread(&workerThread);
        connect(&workerThread, &QThread::finished, worker, &QObject::deleteLater);
        connect(this, &Controller::operate, worker, &Worker::doWork);
        connect(worker, &Worker::resultReady, this, &Controller::handleResults);
        workerThread.start();
    }
    ~Controller() {
        workerThread.quit();
        workerThread.wait();
    }
public slots:
    void handleResults(const QString &);
signals:
    void operate(const QString &);
};
					

然后,会在单独线程中执行 Worker 槽代码。无论如何,把 Worker 槽连接到来自任何对象、任何线程中的任何信号是自由的。跨不同线程连接信号和槽是安全的,得益于机制 队列连接 .

Another way to make code run in a separate thread, is to subclass QThread and reimplement run ()。例如:

class WorkerThread : public QThread
{
    Q_OBJECT
    void run() override {
        QString result;
        /* ... here is the expensive or blocking operation ... */
        emit resultReady(result);
    }
signals:
    void resultReady(const QString &s);
};
void MyObject::startWorkInAThread()
{
    WorkerThread *workerThread = new WorkerThread(this);
    connect(workerThread, &WorkerThread::resultReady, this, &MyObject::handleResults);
    connect(workerThread, &WorkerThread::finished, workerThread, &QObject::deleteLater);
    workerThread->start();
}
					

在该范例中,线程会在 run 函数有返回之后退出。没有任何事件循环会运行在线程中,除非调用 exec ().

It is important to remember that a QThread instance 活在 实例化它的旧线程,而不是新线程调用 run (). This means that all of QThread 's queued slots will execute in the old thread. Thus, a developer who wishes to invoke slots in the new thread must use the worker-object approach; new slots should not be implemented directly into a subclassed QThread .

当子类化 QThread , keep in mind that the constructor executes in the old thread while run () 在新线程中执行。若从两者函数访问成员变量,则变量是从 2 不同线程被访问。检查这样做是安全的。

注意: 必须小心,当与跨不同线程的对象进行交互时。见 同步线程 了解细节。

管理线程

QThread will notifiy you via a signal when the thread is started () 和 finished (),或可以使用 isFinished () 和 isRunning () 去查询线程的状态。

可以停止线程通过调用 exit () 或 quit ()。在极端情况下,可能希望强制 terminate () 执行线程。然而,这样做是危险的且不鼓励。请阅读文档编制为 terminate () 和 setTerminationEnabled () 为详细信息。

从 Qt 4.8 起,解除活在刚结束线程中的对象的分配是可能的,通过连接 finished () 信号到 QObject::deleteLater ().

使用 wait () 去阻塞调用线程,直到其它线程已执行完成 (或直到指定时间已过去)。

QThread also provides static, platform independent sleep functions: sleep (), msleep (),和 usleep () 分别允许完整秒、毫秒及微秒分辨率。这些函数是在 Qt 5.0 公开的。

注意: wait () 和 sleep () 函数一般是不必要的,因为 Qt 是事件驱动型框架。代替 wait (),考虑监听 finished () 信号。代替 sleep () 函数,考虑使用 QTimer .

静态函数 currentThreadId () 和 currentThread () return identifiers for the currently executing thread. The former returns a platform specific ID for the thread; the latter returns a QThread 指针。

要选取赋予线程的名称 (作为标识通过命令 ps -L 例如在 Linux),可以调用 setObjectName() 在启动线程之前。若不调用 setObjectName() ,赋予线程的名称将是线程对象运行时类型的类名 (例如: "RenderThread" 在案例 Mandelbrot 范例 , as that is the name of the QThread subclass). Note that this is currently not available with release builds on Windows.

另请参阅 Qt 中的线程支持 , QThreadStorage , 同步线程 , Mandelbrot 范例 , 信号量范例 ,和 等待条件范例 .

成员类型文档编制

enum QThread:: Priority

此枚举类型指示操作系统应如何调度新近创建的线程。

常量 描述
QThread::IdlePriority 0 才调度,当没有其它线程在运行时。
QThread::LowestPriority 1 经常比 LowPriority 更少调度。
QThread::LowPriority 2 经常比 NormalPriority 更少调度。
QThread::NormalPriority 3 操作系统的默认优先级。
QThread::HighPriority 4 经常比 NormalPriority 更多调度。
QThread::HighestPriority 5 经常比 HighPriority 更多调度。
QThread::TimeCriticalPriority 6 尽可能经常调度。
QThread::InheritPriority 7 使用如创建线程的相同优先级。这是默认。

成员函数文档编制

QThread:: QThread ( QObject * parent = Q_NULLPTR)

构造新的 QThread 去管理新线程。 parent 拥有所有权对于 QThread . The thread does not begin executing until start () 被调用。

另请参阅 start ().

QThread:: ~QThread ()

销毁 QThread .

注意:删除 QThread 对象不会停止其管理的线程的执行。删除正运行 QThread (即 isFinished () 返回 false ) 会导致程序崩溃。等待 finished () 信号先于删除 QThread .

[static] QThread *QThread:: currentThread ()

返回指针指向 QThread 其管理目前正执行线程。

[static] Qt::HANDLE QThread:: currentThreadId ()

返回目前执行线程的线程句柄。

警告: 由此函数返回的句柄可用于内部目的,且不应被用于任何应用程序代码中。

警告: On Windows, the returned value is a pseudo-handle for the current thread. It can't be used for numerical comparison. i.e., this function returns the DWORD (Windows-Thread ID) returned by the Win32 function getCurrentThreadId(), not the HANDLE (Windows-Thread HANDLE) returned by the Win32 function getCurrentThread().

[virtual] bool QThread:: event ( QEvent * event )

重实现自 QObject::event ().

QAbstractEventDispatcher *QThread:: eventDispatcher () const

Returns a pointer to the event dispatcher object for the thread. If no event dispatcher exists for the thread, this function returns 0.

该函数在 Qt 5.0 引入。

另请参阅 setEventDispatcher ().

[protected] int QThread:: exec ()

进入事件循环并等待,直到 exit () 被调用,返回值被传递给 exit ()。返回值为 0 若 exit () 被调用凭借 quit ().

此函数意味着被调用从 run ()。它是必要的,去调用此函数以开始事件处理。

另请参阅 quit () 和 exit ().

void QThread:: exit ( int returnCode = 0)

告诉线程的事件循环采用返回代码退出。

在调用此函数之后,线程离开事件循环并返回从调用 QEventLoop::exec ()。 QEventLoop::exec () 函数返回 returnCode .

按约定, returnCode 0 意味着成功,任何非零值指示出错。

注意:不像同名 C 库函数,此函数 does 返回给调用者 -- 它停止事件处理。

没有 QEventLoop 会在此线程中被再次启动,直到 QThread::exec () 已被再次调用。若事件循环在 QThread::exec () 不在运行,则下一调用 QThread::exec () 也会立即返回。

另请参阅 quit () 和 QEventLoop .

[signal] void QThread:: finished ()

从关联线程发射此信号,在刚好完成线程执行前。

当发射此信号时,事件循环已停止运行。线程中没有更多要处理事件,除延期删除事件外。此信号可以连接到 QObject::deleteLater (),去释放在该线程中的对象。

注意: 若关联线程被终止使用 terminate (),从哪个线程发出此信号就是未定义的。

注意: 这是私有信号。它可以用于信号连接,但不能由用户发射。

另请参阅 started ().

[static] int QThread:: idealThreadCount ()

Returns the ideal number of threads that can be run on the system. This is done querying the number of processor cores, both real and logical, in the system. This function returns -1 if the number of processor cores could not be detected.

bool QThread:: isFinished () const

返回 true 若线程已完成;否则返回 false .

另请参阅 isRunning ().

bool QThread:: isInterruptionRequested () const

返回 true,若在此线程中正运行的任务应被停止。中断可以被请求通过 requestInterruption ().

此函数可以被用于使长时间运行的任务能完全中断。从不检查 (或处理) 由此函数返回的值是安全的,不管怎样,在长时间运行函数中定期这样做是明智的。当心不要太频繁调用它,以保持较低开销。

void long_task() {
     forever {
        if ( QThread::currentThread()->isInterruptionRequested() ) {
            return;
        }
    }
}
					

该函数在 Qt 5.2 引入。

另请参阅 currentThread () 和 requestInterruption ().

bool QThread:: isRunning () const

返回 true 若线程正在运行;否则返回 false .

另请参阅 isFinished ().

int QThread:: loopLevel () const

返回线程的当前事件循环级别。

注意: 这只可以在线程本身内被调用,即:当它是当前线程时。

该函数在 Qt 5.5 引入。

[static] void QThread:: msleep ( unsigned long msecs )

强制当前线程休眠 msecs 毫秒。

另请参阅 sleep () 和 usleep ().

Priority QThread:: priority () const

返回正运行线程的优先级。若线程未在运行,此函数返回 InheritPriority .

该函数在 Qt 4.1 引入。

另请参阅 Priority , setPriority (),和 start ().

[slot] void QThread:: quit ()

告诉线程的事件循环采用返回代码 0 (成功) 退出。相当于调用 QThread::exit (0).

此函数什么都不做,若线程没有事件循环。

另请参阅 exit () 和 QEventLoop .

void QThread:: requestInterruption ()

请求线程的中断。该请求是建议性的,且由在线程上运行的代码决定是否以及如何处理此请求。此函数不会停止在线程中运行的任何事件循环,也不会以任何方式终止它。

该函数在 Qt 5.2 引入。

另请参阅 isInterruptionRequested ().

[virtual protected] void QThread:: run ()

线程的起点。先调用 start (),新近创建的线程调用此函数。默认实现只需调用 exec ().

可以重实现此函数以促进高级线程管理。来自此方法的返回将结束线程的执行。

另请参阅 start () 和 wait ().

void QThread:: setEventDispatcher ( QAbstractEventDispatcher * eventDispatcher )

把线程的事件分派程序设为 eventDispatcher 。这才可能,只要尚未为线程安装事件分派程序。也就是说,在启动线程之前采用 start (),或在主线程情况下,先于 QCoreApplication 被实例化。此方法拥有对象的所有权。

该函数在 Qt 5.0 引入。

另请参阅 eventDispatcher ().

void QThread:: setPriority ( Priority priority )

此函数设置 priority 为正运行线程。若线程未在运行,此函数什么都不做并立即返回。使用 start () 去启动线程采用特定优先级。

priority 自变量可以是任意值在 QThread::Priority 枚举除了 InheritPriorty .

priority 参数的效果取决于操作系统的调度策略。尤其, priority 会被忽略,在不支持线程优先级的系统中 (如在 Linux,见 http://linux.die.net/man/2/sched_setscheduler 了解更多细节)。

该函数在 Qt 4.1 引入。

另请参阅 Priority , priority (),和 start ().

void QThread:: setStackSize ( uint stackSize )

把线程的最大堆栈尺寸设为 stackSize 。若 stackSize 大于 0,最大堆栈尺寸被设为 stackSize 字节,否则,最大堆栈尺寸由操作系统自动确定。

警告: 大多数操作系统对线程堆栈尺寸,有最小和最大限制。线程将无法启动,若堆栈尺寸超出这些限制。

另请参阅 stackSize ().

[static protected] void QThread:: setTerminationEnabled ( bool enabled = true)

启用 (或禁用) 当前线程的终止,基于 enabled 参数。线程必须已被启动由 QThread .

enabled 为 false,终止被禁用。未来调用 QThread::terminate () 将立即返回没有效果。相反,终止被延期,直到终止被启用。

enabled 为 true,终止被启用。未来调用 QThread::terminate () 将正常终止线程。若终止已被延期 (即: QThread::terminate () 被调用采用终止被禁用),此函数将终止调用线程 immediately 。注意:此函数不会返回,在此情况下。

另请参阅 terminate ().

[static] void QThread:: sleep ( unsigned long secs )

强制当前线程休眠 secs 秒。

另请参阅 msleep () 和 usleep ().

uint QThread:: stackSize () const

返回线程的最大堆栈尺寸 (若设置采用 setStackSize ());否则返回 0。

另请参阅 setStackSize ().

[slot] void QThread:: start ( Priority priority = InheritPriority)

开始执行线程通过调用 run ()。操作系统将调度线程根据 priority 参数。若线程已经在运行,此函数什么都不做。

priority 参数的效果取决于操作系统的调度策略。尤其, priority 会被忽略,在不支持线程优先级的系统中 (如在 Linux,见 sched_setscheduler 文档编制了解更多细节)。

另请参阅 run () 和 terminate ().

[signal] void QThread:: started ()

此信号被发射当关联线程开始执行时,前于 run () 函数被调用。

注意: 这是私有信号。它可以用于信号连接,但不能由用户发射。

另请参阅 finished ().

[slot] void QThread:: terminate ()

终止线程的执行。线程可能 (或不可能) 被立即终止,取决于操作系统的调度策略。使用 QThread::wait () 在 terminate() 之后,来确保。

当线程被终止时,等待线程完成的所有线程都将被唤醒。

警告: 此函数是危险的,且不鼓励使用。线程可以在其代码路径中的任何点被终止。线程可以被终止,当修改数据时。线程没有机会在本身、解锁任何保持互斥、等之后被清理。简而言之,若绝对有必要才使用此函数。

终止可以被明确启用 (或禁用) 通过调用 QThread::setTerminationEnabled ()。当终止被禁用时,调用此函数会导致终止被延期,直到终止被重新启用。见文档编制 QThread::setTerminationEnabled () 了解更多信息。

另请参阅 setTerminationEnabled ().

[static] void QThread:: usleep ( unsigned long usecs )

强制当前线程休眠 usecs 微秒。

另请参阅 sleep () 和 msleep ().

bool QThread:: wait ( unsigned long time = ULONG_MAX)

阻塞线程,直到满足这些条件之一:

  • 关联此线程的 QThread 对象已执行完成 (即:当它返回从 run ())。此函数将返回 true,若线程已完成。它也返回 true,若线程尚未被启动。
  • time milliseconds has elapsed. If time is ULONG_MAX (the default), then the wait will never timeout (the thread must return from run ()). This function will return false if the wait timed out.

这提供的功能类似 POSIX pthread_join() 函数。

另请参阅 sleep () 和 terminate ().

[static] void QThread:: yieldCurrentThread ()

把当前线程的执行产生到另一可运行线程,若有的话。注意:操作系统决定切换到哪个线程。