c++ - pthread 2 信号和槽包装器 mit QEventLoop

标签 c++ multithreading qt signals fuse

问题

我目前正在将 FUSE 与 qt5 放在一起。 Qt 和 FUSE 之间还没有桥梁,FUSE 主线程(产生其他工作的 FUSE 线程)和 QCoreApplication 只是并排运行。

但我希望能够使用 Qt 的 SIGNALS 和 SLOTS 在基于 QObject 的对象和 [0] 中所示的 pthread 的 Read(..) 函数之间发送和接收数据。

问题

现在我想更改 [0] 中的 Read(..) 函数以使用 Qt 的 SIGNALS 和 SLOTS 从基于 QObject 的类中检索数据。从 pthread 发送信号有效但没有明确的 QEventLoop 我无法收到回复。因此我查看了 [1] 中的代码,它的设计非常出色,但我还没有让它工作。

伪代码(取自[1]):

QNetworkAccessManager qnam;
QNetworkReply *reply = qnam.get(QNetworkRequest(QUrl(...)));
QEventLoop loop;
QObject::connect(reply, SIGNAL(finished()), &loop, SLOT(quit()));
loop.exec();
/* reply has finished, use it */

看起来很有趣,我只需要一个类似于 QNetworkReply 的 QObject 派生类来处理请求。

当我使用该代码时,我遇到了一个问题,即我的 QNetworkReply 实现不会等待 loop.exec() 运行,然后循环不会接收到 finished() 信号。

但是没有比生成 QEventLoop 更容易的事情了吗?

注意:[1] 示例中的 QNetworkReply 和 QNetworkAccessManager 是在 pthread 中生成的,但是我需要能够使用 SIGNALS 和 SLOTS 与 QCoreApplication 的偶数队列进行通信,因为对象中的数据它来自不同的 QThread(在此 QCoreApplication 或特殊的 QThread)。

使用 Qt::QueuedConnection

我还找到了 [2],也许:

connect(src, SIGNAL(signal-signature), dest, SLOT(slot-signature), Qt::QueuedConnection);

这就是我想要的,但我对此表示怀疑。

链接

最佳答案

您可能面临的是 QNetworkAccessManager internally uses threads to process http requests .这就是为什么它“不等待”你。修复它需要一个相当简单的修改:

QNetworkAccessManager qnam;
QEventLoop loop;
QNetworkReply *reply = qnam.get(QNetworkRequest(QUrl(...)));
QObject::connect(reply, SIGNAL(finished()), &loop, SLOT(quit()));
if (!reply->isFinished()) loop.exec();

在多线程中使用QObjects的注意事项

当作为信号源的对象存在于(实例化于)与具有槽的对象的线程不同的线程中时,连接将属于 QueuedConnection。自动输入。

真正的问题是:每个 QObject具有线程亲和性。默认亲和性是实例化对象的线程。您不应该直接从其他线程使用此类对象。

您可能正在做的是在同一个线程中实例化发送方和接收方对象,然后从另一个线程发出信号。这是潜在错误的根源,如果此类对象的用户强制进行非自动直接连接,则会导致未定义的行为。

无论何时emit object->signal(...) ,下面的不变量应该成立:

Q_ASSERT(QThread::currentThread() == object->thread());

随意在每个 emit() 前面添加那些不变的检查您明确执行的内容。

如果断言失败,需要使用QObject::moveToThread将对象移动到要触发其信号的线程。你可以获得QThread对于给定的 pthread调用QThread::currentThread()来自 pthread 中运行的代码. QThread 的实例将自动为您创建 :)

关于c++ - pthread 2 信号和槽包装器 mit QEventLoop,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19426900/

相关文章:

c++ - 在二维 vector 中找到一个元素,然后将其删除

c++ - 使用 QtConcurrent 加载 Pixmap 并绘制它

c++ - 编写接受代码输入的键盘驱动程序

c++ - cuda随机数并不总是返回0和1

c++ - 我什么时候必须释放内存?

python - 在 python 中的类中启动无限循环线程后继续执行代码

java - 显式调用 Runnable.run

c++ - 当我的数组达到一定大小时 Qt 不工作

c++ - 序列化 QGraphicsScene 内容

c++ - Qt 应用程序 C++ 的自定义小部件