qt執行緒同步之條件等待
阿新 • • 發佈:2019-01-09
本文章使用QWaitCondition實現執行緒間的同步
#include <QApplication> #include <QMutex> #include <QThread> #include <QSemaphore> #include <QWaitCondition> #include <iostream> using namespace std; // 需要生產的資料量 const int DATA_SIZE = 100; // 指定緩衝區的大小 const int BUF_SIZE = 10; // 存/取資料的緩衝區 int buf[BUF_SIZE] = {0}; QMutex mutex;// 實現執行緒間的互斥 // 當緩衝區沒有填充滿時,該條件被觸發(反之,當緩衝區被填充滿了,該條件會阻塞執行緒) QWaitCondition bufIsNotFull; // 當緩衝區不為空時,該條件被觸發(反之,當緩衝區為空時,該條件會阻塞執行緒) QWaitCondition bufIsNotEmpty; // 統計生產的且還沒有被消費的資料量 int nUsedSapce = 0; class CProducer : public QThread { protected: virtual void run() { for (int i = 0 ; i < DATA_SIZE ; ++i) { mutex.lock(); if (nUsedSapce == BUF_SIZE)// 如果緩衝區已填滿,則等待緩衝區中的資料被取走 bufIsNotFull.wait(&mutex);// 在阻塞執行緒前,bufIsNotFull會解鎖互斥量,然後阻塞執行緒,等待bufIsNotFull條件物件被觸發,在返回前,會重新鎖定互斥量,然後返回 buf[i%BUF_SIZE] = qrand() % 50 + 1;// 儲存生產的資料 cout << "produce data is :" << buf[i%BUF_SIZE] << endl; ++nUsedSapce;// 生產了一個數據 bufIsNotEmpty.wakeAll();// 喚醒所有等待bufIsNotEmpty條件的執行緒 mutex.unlock(); } } }; class CConsumer : public QThread { protected: virtual void run() { for (int i = 0 ; i < DATA_SIZE ; ++i) { mutex.lock(); if (nUsedSapce == 0)// 如果緩衝區為空,那麼等待緩衝區被填充資料 bufIsNotEmpty.wait(&mutex);// 在阻塞執行緒前,bufIsNotEmpty會解鎖互斥量,然後阻塞執行緒,等待bufIsNotEmpty條件物件被觸發,在返回前,bufIsNotEmpty會重新鎖定互斥量,然後返回 int nData = buf[i%BUF_SIZE];// 取出要消費的資料 cout << "consume data is: " << nData << endl; --nUsedSapce;// 消費了一個數據 bufIsNotFull.wakeAll();// 喚醒所有等待bufIsNotFull條件的執行緒 mutex.unlock(); } } }; int main(int argc, char *argv[]) { QApplication app(argc, argv); CProducer producer; CConsumer consumer; producer.start(); consumer.start(); producer.wait(); consumer.wait(); return app.exec(); }