首頁  >  文章  >  Java  >  什麼是記憶體模型,為什麼需要它?

什麼是記憶體模型,為什麼需要它?

零下一度
零下一度原創
2017-06-25 10:32:562145瀏覽

JAVA記憶體模型

  在多執行緒這一系列中,不去探究記憶體模型的底層

一、什麼是記憶體模型,為什麼需要它

  在在現代多核心處理器中,每個處理器都有自己的緩存,定期的與主記憶體進行協調;

  想要確保每個處理器在任意時刻知道其他處理器正在進行的工作,將需要很大的開銷;且通常是沒必要的

  我們只有在需要跨線程共享資料時,才需要知道資訊;而在JAVA中就是透過正確的同步來實現

# 1.重排序

    如下:判斷輸出的值將十分困難

public class PossibleReordering {static int x = 0, y = 0;static int a = 0, b = 0;/** * 判断输出值将会非常困难:
     * 1:多线程之间的切换,导致可能的输出值:(0,1)(1,0)(1,1)
     * 2.指令重排序:one线程如a=1和x=b之间重排序,x=b(0),然后other线程被调度执行y=a(0),将导致(0,0)     */public static void main(String[] args) throws InterruptedException {
        Thread one = new Thread(new Runnable() {public void run() {
                a = 1;
                x = b;
            }
        });
        Thread other = new Thread(new Runnable() {public void run() {
                b = 1;
                y = a;
            }
        });
        one.start();
        other.start();
        one.join();
        other.join();
        System.out.println("( " + x + "," + y + ")");
    }
}

 

   2.JAVA內存模型簡介

偏序關係:反對稱、自反和傳遞屬性;但是對於任意的兩個元素A和B,並不一定滿足A偏向B或B偏向A的關係

      如:A和B之間我比較偏向B,但是我沒必要明確的做出選擇

    JMM為程序中所有的操作定義了一個偏序關係,稱之為Happens-Before;要想保證執行B操作的線程看到執行A操作的線程的結果,無論AB是否在同一線程,必須滿足Happens-Before關係,否則JVM就會對其重排序

#    

#如:加鎖操作,就可以預知執行順序,多個執行緒之間就符合Happens-Before,不加鎖則無法判斷執行緒之間的調度,

  3.發布

     真正原因:發布一個共享對象 和 在另一個線程中訪問該對象之間沒有Happens-Before關係;由於指令重新排序,導致對象沒有正確構建則被發布

public class UnsafeLazyInitialization {private static Resource resource;/** * 除了竟态条件问题检查后执行,还有不安全发布的问题
     * 如:一个线程A进来,看到resource为null,则实例化并返回;另一个线程B进来看到resource不为null直接返回
     * 如果在线程A中对resource进行了修改,则可能在线程B中看不到resource的正确状态     */public static Resource getInstance() {if (resource == null)
            resource = new Resource(); // unsafe publicationreturn resource;
    }static class Resource {
    }
}

 

     

 

#

以上是什麼是記憶體模型,為什麼需要它?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn