Java併發編程的藝術 記錄(三)

Java內存模型

  併發編程的兩個關鍵問題:程序員

    1.線程之間如何通信。編程

    2.線程間如何同步。數組

  兩種方式:共享內存和消息傳遞。緩存

  Java的併發採用的是共享內存模型,Java線程之間的通訊老是隱式進行,整個通訊過程對程序員徹底透明。

併發

  實例域、靜態域和數組元素都存儲在堆內存中,堆內存在線程之間共享。Java線程之間的通訊由Java內存模型:JMM控制。app

  JMM經過控制主內存與每一個線程的本地內存之間的交互,來爲Java程序員提供內存可見性保證 。優化

  重排序分3種類型:
    1)編譯器優化的重排序。編譯器在不改變單線程程序語義的前提下,能夠從新安排語句的執行順序。
    2)指令級並行的重排序。現代處理器採用了指令級並行技術(Instruction-LevelParallelism,ILP)來將多條指令重疊執行。若是不存在數據依賴性,處理器能夠改變語句對應機器指令的執行順序。
    3)內存系統的重排序。因爲處理器使用緩存和讀/寫緩衝區,這使得加載和存儲操做看上去多是在亂序執行 。spa

  對於處理器重排序,JMM的處理器重排序規則會要求Java編譯器在生成指令序列時,插入特定類型的內存屏障(Memory Barriers,Intel稱之爲Memory Fence)指令,經過內存屏障指令來禁止特定類型的處理器重排序 。
線程

  happens-before規則以下:
    1.·程序順序規則:一個線程中的每一個操做,happens-before於該線程中的任意後續操做。
    2.·監視器鎖規則:對一個鎖的解鎖,happens-before於隨後對這個鎖的加鎖。
    3.·volatile變量規則:對一個volatile域的寫,happens-before於任意後續對這個volatile域的讀。
    4.·傳遞性:若是A happens-before B,且B happens-before C,那麼A happens-before C。
blog

  順序一致性,可見性保證。全部的操做按程序的順序執行,而JMM中臨界區內的代碼能夠重排序。

  volatile寫的內存語義以下。
    當寫一個volatile變量時,JMM會把該線程對應的本地內存中的共享變量值刷新到主內存。

  volatile讀的內存語義以下。
    當讀一個volatile變量時,JMM會把該線程對應的本地內存置爲無效。線程接下來將從主內存中讀取共享變量。

  ReentrantLock:有公平鎖和非公平鎖

  Java線程之間的通訊4種方式    1)A線程寫volatile變量,隨後B線程讀這個volatile變量。    2)A線程寫volatile變量,隨後B線程用CAS更新這個volatile變量。    3)A線程用CAS更新一個volatile變量,隨後B線程用CAS更新這個volatile變量。    4)A線程用CAS更新一個volatile變量,隨後B線程讀這個volatile變量

相關文章
相關標籤/搜索