有序性
記憶體屏障會提供3個功能:
1)它確保指令重排序時不會把其後面的指令排到記憶體屏障之前的位置,也不會把前面的指令排到記憶體屏障的後面;即在執行到記憶體屏障這句指令時,在它前面的操作已經全部完成;
2)它會強制將對快取的修改操作立即寫入主存;
3)如果是寫操作,它會導致其他cpu中對應的快取行無效。
volatile 的底層實現原理是記憶體屏障,memory barrier(memory fence)
還是那句話,不能解決指令交錯:舉個例子寫屏障僅僅是保證之後的讀能夠讀到最新的結果,但不能保證讀跑到它前面去
而有序性的保證也只是保證了本執行緒內相關**不被重排序
//x、y為非volatile變數
//flag為volatile變數
x =2;
//語句1
y =0
;//語句2
flag =
true
;//語句3
x =4
;//語句4
y =-1;
//語句5
一般實現
public
final
class
singleton
private
static singleton instance = null;
public
static singleton getinstance()
}}return instance;
}}
以上的實現特點是:
會出現的問題就是,第乙個 if 使用了 instance 變數,他在拿取時在 monitor (synchronized 加鎖階段)控制之外,可以越過 monitor 讀取instance 變數的值,而此時synchronized 中的instance構造方法與賦值方法發生指令重排,那麼拿到的是乙個未初始化完畢的單例。
所以對 instance 要使用 volatile 修飾,禁用指令重排
修改過後
public
final
class
singleton
private
static
volatile singleton instance = null;
public
static singleton getinstance()
}}return instance;
}}
引用文章 關鍵字 volatile關鍵字的作用
1.volatile關鍵字是防止在共享的空間發生讀取的錯誤。只保證其可見性,不保證原子性 使用volatile指每次從記憶體中讀取資料,而不是從編譯器優化後的快取中讀取資料,簡單來講就是防止編譯器優化。2.在單任務環境中,如果在兩次讀取變數之間不改變變數的值,編譯器就會發生優化,會將ram中的值賦值...
關鍵字volatile詳解
與關鍵字const一樣,關鍵字volatile也是乙個型別修飾符 type specifier 關於volatile的作用 例如程式清單 volatile int m 10 int k,n m k i volatile將告訴編譯器,整形變數m是隨時發生變化的,每次使用m的時候,都要求從m的位址中找出...
volatile關鍵字 詳解
volatile 關鍵字 volatile關鍵字是一種型別修飾符,用它宣告的型別變數表示可以被某些編譯器未知的因素更改,比如 作業系統 硬體或者其它執行緒等。遇到這個關鍵字宣告的變數,編譯器對訪問該變數的 就不再進行優化,從而可以提供對特殊位址的穩定訪問。使用該關鍵字的例子如下 int volati...