static的強制同步機制 synchronized的同步機制:可以使用this、類字面常亮、特有鎖對象(專門為加鎖使用,無實際意義的對象,此種方式效率更高。)
ReentrantLock(可重入的鎖)
synchronized關鍵字同步的時候,等待的線程将無法控制,隻能死等。
解決方式:ReentrantLock可以使用tryLock(timeout, unit)方法去控制等待獲得鎖的時間,也可以使用無參數的tryLock方法立即傳回,這就避免了死鎖出現的可能性。
synchronized關鍵字同步的時候,不保證公平性,是以會有線程插隊的現象。
解決方式:ReentrantLock可以使用構造方法ReentrantLock(fair)來強制使用公平模式,這樣就可以保證線程獲得鎖的順序是按照等待的順序進行的,而synchronized進行同步的時候,是預設非公平模式的,但JVM可以很好的保證線程不被餓死。
<code>ReentrantLock有這樣一些優點,當然也有不足的地方。最主要不足的一點,就是ReentrantLock需要開發人員手動釋放鎖,并且必須在finally塊中釋放。</code>
在Object中,有一個wait的本地方法;它可以用來協調線程之間的協作。
wait一般情況下最常用的場景是構造一個花銷非常大的對象的時候,比如JDK動态代理在生成代理類的時候就使用了這種方式。JDK6在生成一個代理類之前,會先檢測一個是否正在生成中的辨別,如果正在生成的話,JDK6就會在對象上等待,直到正在生成的代理類生成完畢,然後直接從緩存中擷取。
wait,notify和notifyAll方法在使用前,必須擷取到目前對象的鎖,否則會告訴你非法的監控狀态異常。還有一點,則是如果有多個線程在wait等待,那麼調用notify會随機通知其中一個線程,而不會按照順序通知。換句話說,notify的通知機制是非公平的,notify并不保證先調用wait方法的線程優先被喚醒。notifyAll方法則不存在這個問題,它将通知所有處于wait等待的線程。
JDK的類庫中,有這樣的一個類Condition,來彌補wait方法本身的不足。
wait方法當使用帶參數的方法wait(timeout)或者wait(timeout,nanos)時,無法回報究竟是被喚醒還是到達了等待時間,大部分時候,我們會使用循環(就像上面的例子一樣)來檢測是否達到了條件。
解決方式:Condition可以使用傳回值辨別是否達到了逾時時間。
由于wait,notify,notifyAll方法都需要獲得目前對象的鎖,是以當出現多個條件等待時,則需要依次獲得多個對象的鎖,這是非常惡心麻煩且繁瑣的事情。
解決方式:Condition之需要獲得Lock的鎖即可,一個Lock可以擁有多個條件。
這個類是為了幫助猿友們友善的實作一個這樣的場景,就是某一個線程需要等待其它若幹個線程完成某件事以後才能繼續進行。
這個類是為了幫助猿友們友善的實作多個線程一起啟動的場景,就像賽跑一樣,隻要大家都準備好了,那就開始一起沖。比如下面這個程式,所有的線程都準備好了,才會一起開始執行。
這個類是為了幫助猿友們友善的實作控制數量的場景,可以是線程數量或者任務數量等等。
這個類是為了幫助猿友們友善的實作兩個線程交換資料的場景,使用起來非常簡單。
參考文檔:
<a href="http://blog.csdn.net/ghsau/article/details/7443324">http://blog.csdn.net/ghsau/article/details/7443324</a> <a href="http://www.cnblogs.com/zuoxiaolong/p/con2.html">http://www.cnblogs.com/zuoxiaolong/p/con2.html</a>