QT4 thread和QObject關係詳解

2021-08-26 22:57:29 字數 1753 閱讀 5468

qthread從qobject派生。它發出訊號來表明執行緒開始了或結束了。並且也提供了幾個槽。

更有趣的是,qobject可以在多個程中同時使用,可以發出訊號給另外執行緒的槽,以及向「活在」另外執行緒中的物件郵寄事件。以上之所以能發生,是因為每個初程都被允許擁有它自己的事件迴圈。

qobject是可重入的。它大多數非介面派生類,比如qtimer,qtcpsocket,qftp,和qprocess,也都是可重入的,使得在多個執行緒中同時使用這些類成為可能。但是注意這些類被設計為在乙個執行緒中建立和使用;在乙個執行緒中建立乙個物件然後在另乙個執行緒中呼叫它的方法是不能保證一定能工作的。有三個限制條件要注意:

qobject的兒子必須在建立它爹的執行緒中建立。這表示,你永遠不能將qthread物件(this)作為parent傳給在此thread建立的物件,因為執行緒物件自己就是在另乙個執行緒中建立的。

事件驅動的物件應該只用於乙個執行緒中。這一條尤其應用於定時器和網路模組。比如,你不能在建立物件之外的執行緒中啟動乙個定時器或連線乙個socket。

在實際應用中,最好的方式是把耗時的計算放到主線程中外進行,完成後通知主線程顯示結果。

乙個qobject例項在那個執行緒中建立,就叫做「活」在那個執行緒中。給這個物件的事件們通過執行緒的事件迴圈派發。乙個qobject物件所「活在」的執行緒通過qobject::thread()可以取得。

在擁有物件之外的執行緒中呼叫刪除物件是不安全的,除非你能保證在被刪除時不在處理事件。但可以使用qobject::deletelater(),它會寄出defereddelete事件,物件的執行緒的事件迴圈最終會抓住它。預設下,擁有qobject的執行緒就是建立qobject的執行緒,但在qobject::movetotread()之後就變了。

如果沒有事件迴圈,事件將不能傳給物件。比如,如果你在乙個執行緒中建立乙個qtimer物件,但是沒有再呼叫exec(),那麼qtimer將永不能觸發timeout()訊號。deletelater()也不再能工作。(這些也同樣適用於主線程。)

qobject和它所有的子類都不是執行緒安全的,這也包含整個事件派送系統。要記住,當你從另外執行緒訪問物件時,事件迴圈可能派送事件到你的qobject子類。

如果你呼叫乙個非本執行緒的qobject的子類的函式並且這個物件可能接收事件,你必須用mutex保護所有對你的qobject子類的內部資料的訪問;否則,你可能體驗的什麼叫崩潰。

就像其它物件,qthread物件「活」在建立它的執行緒中,而不是它自己所代表的執行緒中。通常在你的qthread子類中提供槽是不安全的,除非你用mutex保護成員變數。

另一方面,你可以從你的qthread tun()中安全的發出訊號,因為訊號發射是執行緒安全的。

qt支援如下訊號-槽連線型別:

自動連線(預設)- 如果訊號是從接收物件所在的執行緒發出的,其行為與「直接連線」相同。否則,其行為與「佇列連線」相同。

直接連線- 當訊號發出,槽會被立馬呼叫。此槽在發出者的執行緒中執行,而不一定是接收者所在的執行緒。

阻塞的佇列連線- 槽像「佇列連線」那樣被呼叫,除了一點:當前執行緒會阻塞住直到槽返回。注:在同一執行緒中使用此型別的連線將導致死鎖!

唯一連線- 行為與「自動連線」相同,但連線必須在無複製品時才能建立。也就是,如果在相同的兩個物件之間已經建立了同乙個訊號到同乙個槽的連線,那麼連線就不能建立,connect()返回false。

連線型別可以通過給connect()傳遞乙個額外的引數來指定。注意當接收者和傳送者位於不同的執行緒中時,使用「直接連線」,如果事件迴圈是執行於接收者的執行緒中,此時是不安全的,同理呼叫位於另外執行緒的物件的任何函式都是不安全的。

qobject::connect()本身是執行緒安全的。

Ubuntu下安裝Qt4和PyQt4

qt是1991年奇趣科技開發的乙個跨平台的c 圖形使用者介面應用程式框架。它提供給應用程式開發者建立藝術級的圖形使用者介面所需的所用功能。qt很容易擴充套件,並且允許真正地元件程式設計。基本上,qt 同 x window 上的 motif,openwin,gtk 等圖形界 面庫和 windows 平...

Qt學習筆記 4 QTimer和QTime

qtimer是乙個計時器類 它的使用分三步,建立物件,連線signal和slot函式,start qtimer timer new qtimer this connect timer,signal timeout this,slot update timer start 1000 其中,signal...

Qt VS 修改和除錯 Qt4VSAddin 手記

雖然最近qt杯具到被賣,但qtcreator和qmake仍然是比較不錯的選擇,再配上qt4vsaddin 編碼除錯都不成問題,但是非qt工程不能轉換成pro工程,所以嘗試下使其支援。參考 根據說明先編譯 qaxserver.prf,則增加一句 isempty qt source tree qt so...