首页 > 解决方案 > Qt C++ 是静态thread_local QNetworkAccessManager 线程应用程序的好选择吗?

问题描述

我正在使用用 Qt (C++) 编写的线程应用程序。

我需要经常从单独的线程发出获取/发布请求。

Qt 文档说:

一个 QNetworkAccessManager 实例对于整个 Qt 应用程序应该足够了。由于QNetworkAccessManager是基于QObject的,所以只能从它所属的线程中使用。

static thread_local QNetworkAccessManager我的目的的好选择吗?

标签: c++qtqtnetwork

解决方案


不,不是一个好的选择。

您不应该创建静态或全局QObject子类实例,因为您通常需要在创建Qt 应用程序对象之后创建它们(很多 Qt 东西依赖于已经存在的应用程序对象)。C++ 并没有真正提供对何时实际创建静态对象的很好的控制,在这里您希望拥有这种控制。

只需使用指针并new创建QNetworkAccessManager实例,只要你想要的就可以。您可以直接在正确的线程中创建它们,或者您可以在其他一些(通常是主)线程中创建它们并将它们移动到正确的线程。

为了使它们正确销毁,当它们没有自然父级时(因为父级必须存在于同一个线程中!),将它们的线程QThread::finished信号连接到对象QObject::deleteLater插槽,当线程完成时它们将被干净地删除。


如果你想要一个普通函数,它使用当前线程的 QNAM 实例,你可以有 thread-local static pointer。就像是

static thread_local *thread_qnam;

void myfunc() {
    if (!thread_qnam) {
        thread_qnam = new QNetworkAccessManager;
        connect(QThread::currentThread, &QThread::finished(), thread_qnam, &QObject::deleteLater);
        // Whatever other setup you need.
        // It'd probably be good idea to wrap this in a function.
    }
    // Use thread_qnam...
}

推荐阅读