QSemaphore 是 Qt 框架中用于线程间同步的类。它可以用于控制对共享资源的访问,以避免多个线程同时访问同一资源而导致的问题。以下是一个使用 QSemaphore 的简单示例,说明如何在线程间实现交互:
示例:生产者-消费者问题
假设有两个线程:一个生产者线程和一个消费者线程。生产者线程生成数据,而消费者线程消费这些数据。我们使用一个队列来存储这些数据,并使用 QSemaphore 来控制对队列的访问。
定义共享资源:我们有一个队列(例如,使用 QQueue)用于存储数据。
定义信号量:使用 QSemaphore 来控制对队列的访问。例如,我们有一个信号量用于控制生产者线程向队列中添加数据,另一个信号量用于控制消费者线程从队列中取出数据。
实现线程:
生产者线程:生成数据,等待信号量允许,将数据放入队列,然后释放信号量。
消费者线程:等待信号量允许,从队列中取出数据,处理数据,然后释放信号量。
代码示例
下面是一个简单的示例代码:
#include <QCoreApplication>
#include <QQueue>
#include <QSemaphore>
#include <QThread>
#include <QDebug>
// 共享资源 - 队列
QQueue<int> dataQueue;
// 控制向队列添加数据的信号量
QSemaphore addSemaphore(1); // 初始化为1,允许一个线程进入临界区
// 控制从队列中取出数据的信号量
QSemaphore removeSemaphore(0); // 初始化为0,阻止任何线程进入临界区
class Producer : public QThread {
protected:
void run() override {
for (int i = 0; i < 5; ++i) {
addSemaphore.acquire(); // 等待允许向队列添加数据
dataQueue.enqueue(i); // 添加数据到队列
qDebug() << "Producer added:" << i;
removeSemaphore.release(); // 允许一个线程从队列中取出数据
}
}
};
class Consumer : public QThread {
protected:
void run() override {
while (!dataQueue.isEmpty()) {
removeSemaphore.acquire(); // 等待允许从队列中取出数据
int value = dataQueue.dequeue(); // 从队列中取出数据
qDebug() << "Consumer consumed:" << value;
addSemaphore.release(); // 允许一个线程向队列添加数据
}
}
};
int main(int argc, char *argv[]) {
QCoreApplication a(argc, argv);
Producer producer;
Consumer consumer;
producer.start();
consumer.start();
producer.wait();
consumer.wait();
return a.exec();
}
这个例子中,生产者和消费者通过 QSemaphore 实现了同步,确保了数据的安全生产和消费。