2013-04-05 41 views
2

考慮以下情況:Qt同步在這裏不可能嗎?

class SomeClass : public QObject 
{ 
    Q_OBJECT 
private: 
    unsigned long long someVar; 

public: 
    unsigned long long getSomeVar(){ 
     return someVar; 
    void threadFunc(); 
} 

threadFunc()將在一個新的線程(你猜對了)被調用,它會看起來像這樣:

void SomeClass::threadFunc() 
{ 
    ++someVar; 
    // Do stuff... 
} 

現在,在另一個線程,我想閱讀someVar。我通過致電getSomeVar()來這樣做。但是,需要同步。我怎麼做?對於somevar的線程,同步並不困難。它只是

void SomeClass::threadFunc() 
{ 
    mut.lock(); 
    ++someVar; 
    mut.unlock(); 
    // Do stuff... 
} 

QMutex mut添加在類聲明中。但我如何同步getSomeVar()?我不能只是說:

unsigned long long getSomeVar(){ 
    mut.lock(); 
    return someVar; 
    mut.unlock(); 
} 

mut.unlock()絕不會因爲之前的return語句來的調用。

我知道,通常這樣的衝突寫避免...

...但在這種情況下,我需要的互斥體是相同的內部getSomeVar()threadFunc()。我試過

unsigned long long getSomeVar(){ 
    // constructing mutex from mut (which is the class' mutex) 
    QMutex mutex(mut); 
    // mutex-constructor calls mut.lock() 
    return someVar; 
    // mutex-destructor calls mut.unlock() 
} 

但互斥體的構造函數是私有的。

我能在這裏做什麼?

+0

在Qt的許多情況下,您可以避免使用信號和插槽進行顯式同步。不知道在您的具體使用中是否會造成過多的流失。 – Digikata 2013-04-05 21:17:17

+0

信號和插槽無疑是更好的方法,但是如果每次更改'someVar'時都會觸發事件,它們也會嚴重影響性能。所以我並不是真的想要信號和插槽。 – 2013-04-05 21:20:24

+0

@MaxBeikirch - 人們經常會爲基本功能混淆信號和插槽,信號和插槽是用於信號傳輸的,它們不打算在嚴格的性能循環中被解僱。不僅內聯它們是不可能的,而且開銷非常巨大,更不用說線程間連接排隊了,而且非常緩慢。當你運行你的任務時,你會使用一次連接,一旦完成任務,也可能定期獲取進度,但是當然你不會依賴信號和插槽來傳輸大量數據或者在緊密循環中運行。 – dtech 2013-04-05 21:23:49

回答

7

您正在尋找QMutexLocker

{ 
    QMutexLocker locker(&mut); 
    ... 
} 

// Goes out of scope, unlocks the mutex in its destructor 
+0

就是這樣!現在我不知道接受哪個答案:\ – 2013-04-05 21:17:51

2

你混淆了互斥:有每guardable變量只有一個互斥體,但可能有很多嘗試鎖定它!

需要有單獨的鎖類,其中你有每個線程一個實例

struct Lock 
{ 
    QMutex & m_; 
    Lock(QMutex & m) : m_(m) { m_.lock(); } 
    ~Lock() { m_.unlock();} 
}; 

用法:

QMutex mutex; 

void thread_function() 
{ 
    Lock lk(mut); 
    critical_operation(); 
} // unlocks "mutex" as if by magic 

的Qt可能已經提供了這樣一類的。 (標準庫也是這樣做的:對於std::mutex,您有std::lock_guard<std::mutex>。)

+0

就是這樣!現在我不知道接受哪個答案:\ – 2013-04-05 21:17:22

+0

@MaxBeikirch:無論你認爲哪一個最有用。我真的不在乎,如果這樣會更容易... – 2013-04-05 21:17:54

+0

然後我會去找克里斯的答案,就像他幾秒前一樣。 – 2013-04-05 21:24:39