JVM那些事--內存模型

【綜述】
Java內存模型詳細地描述了Java中多線程之間如何通過共享內存進行通信的。
首先,抽象地定義了多線程和主內存之間的關系。
接著,抽象地定義了共享變量被線程讀寫操作間的偏序關系,即happens-before規則。
最后,Java內存模型解決了共享變量被多線程操作的可見性問題。
【主內存和本地內存】
這里抽象地給出線程和主內存間的關系定義:
多個線程間的共享變量存儲在主內存;
每個線程都有一個本地內存,本地內存中保存的是被所屬線程讀寫的共享變量的拷貝;
線程對變量的操作都必須在本地內存中進行,而不能直接讀寫主內存中的共享變量;

其中,本地內存是對高速緩存、寄存器、緩沖區、編譯器優化等軟硬件機制的抽象。


image.png

【happens-before規則】
happens-before規則抽象地定義了多線程對共享變量的讀寫操作的偏序關系,實際上就是定義了在什么條件下一個線程對于共享變量的寫操作對另一個線程可見。
An unlock on a monitor happens-before every subsequent lock on that monitor. (同步鎖和顯式鎖的可見性)

A write to a volatile field happens-before every subsequent read of that field. (volatile共享變量的可見性)

A call to start() on a thread happens-before any actions in the started thread. (start方法的可見性)

All actions in a thread happen-before any other thread successfully returns from a join() on that thread. (join方法的可見性)

The default initialization of any object happens-before any other actions (other than default-writes) of a program. (對象初始化方法的可見性)

程序次序規則:在單線程中,按照代碼的執行順序,(時間上)先執行的操作happen—before(時間上)后執行的操作

傳遞性:如果操作A happen—before操作B,操作B happen—before操作C,那么可以得出A happen—before操作C

線程中斷規則:對線程interrupt()方法的調用happen—before發生于被中斷線程的代碼檢測到中斷時事件的發生。

【案例分析】
注意仔細體會使用較少的volatile(同步鎖、顯式鎖)、較多的跟volatile無關的happens-before規則來保證共享變量操作的可見性
案例1 DCL單例模式中的線程安全問題
試著應用happens-before法則分析,見 http://blog.csdn.net/ns_code/article/details/17359719
案例2 只使用一個volatile變量,就可以保證普通共享變量和其的可見性
http://blog.csdn.net/htq__/article/details/51764156

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容