沒有銀彈,合適與正確的距離


今天在網上查看QThread的信息時找到一篇文章,http://hi.baidu.com/cyclone/blog/item/5fac3bc7ab1b90d1d10060f2.html

文章引述了老外的觀點說什么是QThread的正確使用方式,文章很短,一下子就看完了,看了無非就是說QThread的正確使用方式應該是事件驅動。

的確,標准的Qt程序就應該像這樣:

#include <QCoreApplication>
#include <QDebug>
int main(int argc, char **argv){
QCoreApplication app(argc, argv);
qDebug<<"hello world";
return app.exec();
}

這里潛在的意思是說,如果用Qt,就應該利用其事件循環,所謂的正確的Qt的方式就是事件驅動編程。

事實上,Qt的很多類即使沒有事件循環的存在也能工作得很好,丟棄事件循環的Qt依然有用,只能說,事件循環是充分利用Qt庫的一種合適的方式,但不一定是正確的方式。

並不是為了博取噱頭而故意混淆這樣的概念,事件驅動是為了響應事件而設計的編程方式,像GUI程序基本上只能按事件驅動的方式來設計,用戶隨時可能對其下達指令,它需要捕獲事件來響應用戶,這里潛在的意思就是說,服務用戶的程序就該像一個仆人一樣,沒事的時候等着,隨時隨地待命行事。

但不要忘了,無數的程序都是自己按照既定的“程序”在運行,這才是程序之所以是程序的運行方式,就好像很多的編程書名字那樣,編程就像coke,按着cokebook就能完成任務,設想在廚房的時候,突然出現異步事件,我們可以去查看,程序也能,在Linux下,異步響應可以通過信號來完成。

可以發現,系統級別的中斷提供了打斷運行中的程序的途徑,而用戶級別是沒有辦法像系統那樣可以在執行的代碼中間更換控制流的,所以所謂的事件驅動其實都必須封裝在一個事件循環之中,對於Qt的事件循環,隨意一個函數調用就能阻斷整個事件循環,正因為如此才會因為某一個函數導致整個程序無法響應的現象,不回到事件循環的控制流就無法處理任何的事件,甚至於其引以為傲的信號——槽機制,如果是排隊連接,恐怕也無法處理了。

正因為如此,所謂的QThread的正確方式,只是為了更好地利用事件循環罷了,當然,也為了防止新手陷入迷惑——Qt一直聲稱其簡化了C++的復雜性,而相比之言,一味地強調事件驅動反而更容易被迷惑,畢竟事件驅動的編程方式本身就不簡單,而且,可以設想,順序執行的程序可以很簡單地加入異步事件,那如何在事件編程中加入順序執行的程序呢?換句話說,有沒有簡單的方式可以用一種默認的動作來填補程序等待事件時的時間?這恐怕會使程序更加復雜,就如《C++ GUI Qt4編程》里面展示的那樣,為了保持事件循環的持續響應,引入線程之外的實現方式將導致程序變得晦澀難懂,而引入線程增加的復雜性估計更嚇人。

這讓人想起面向對象和面向過程優越性的爭論,如果拋開具體的應用,無論怎么說,都是有理,也無論如何,都沒道理。從應用層面上說,沒有正確的,只有合適的。


注意!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。



 
  © 2014-2022 ITdaan.com 联系我们: