如何在QThreadPool中多次运行同一个QRunnable?

问题描述 投票:0回答:1

我正在阅读法文书籍“Maîtrisez Qt 5:guide de développement d'applications professionalnelles”来学习Qt。

里面有一段小代码来解释

QThreadPool
:

#include "MaTache.h"
#include <QCoreApplication>
#include <QThreadPool>

int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);

    QThreadPool::globalInstance()->setMaxThreadCount(3);

    for(int i = 0 ; i < 10 ; i++) {
        MaTache *t = new MaTache; // MaTache inherits from QRunnable
        QThreadPool::globalInstance()->start(t);
    }
    
    QThreadPool::globalInstance()->waitForDone();

    return 0;
}

但是,我在官方 QT 文档中读到了这个建议:

使用相同的 QRunnable 多次调用 QThreadPool::start() 当启用 autoDelete 时会产生竞争条件,但不会 推荐。

另外,我在官方文档中阅读了有关

QThreadPool::waitForDone(QDeadlineTimer deadline = QDeadlineTimer::Forever)
的信息:

等到截止日期到期所有线程退出并删除所有线程 线程池中的线程。如果所有线程都已完成,则返回 true 删除;否则返回 false。

所以,我有几个问题:

  1. 当建议说“相同的 QRunnable”时,这是同一个类还是该类的同一个实例?这里我们使用相同的类但不是相同的实例,那么是否存在竞争条件?
  2. 如果我们在调用 start 之前添加
    t->setAutoDelete(false);
    (因为默认情况下为 true),我们如何手动删除
    QRunnable
  3. 上一个问题讲的是
    QRunnable
    的删除,
    QThreadPool::waitForDone
    宁愿删除线程,我可以根据
    QRunnable
    的删除方式无所谓地使用吗?
c++ qt threadpool
1个回答
0
投票

这是来自问题评论和文档的this部分的三个答案:

请注意,如果以下情况,线程池将获得可运行的所有权:

runnable->autoDelete()
返回true,runnable将被删除
runnable->run()
返回后自动由线程池执行。如果
runnable->autoDelete()
返回 false,可运行的所有权仍然存在 与来电者一起。

  1. 文档的建议,谈论使用相同的

    QThreadPool::start()
    多次调用
    QRunnable
    时的竞争条件(当启用
    autoDelete
    时)只是关于重复删除同一实例的可能性
    QRunnable
    。在此示例中,我们从不使用同一实例调用
    QThreadPool::start
    ,因此不存在竞争条件。

  2. 如果我们在调用开始之前添加

    t->setAutoDelete(false);
    (默认情况下为true),我们可以通过保留地址并在
    QRunnable
    之后调用delete来手动删除之后的
    QThreadPool::globalInstance()->waitForDone();

  3. 由于

    QThreadPool::waitForDone
    QRunnable
    更会删除线程,因此可以在
    QRunnable
    删除模式(带/不带自动删除)上无差别地使用。

© www.soinside.com 2019 - 2024. All rights reserved.