日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > java >内容正文

java

Java 复习 —— JMM基础

發布時間:2025/7/14 java 31 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Java 复习 —— JMM基础 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

2019獨角獸企業重金招聘Python工程師標準>>>

基本內容

1、共享變量在線程間的可見性

2、synchronized實現可見性

3、volatile 實現可見性

1)指令重排序

2)as-if-serial

3)volatile 使用注意事項

4、volatile和synchronized的比較

1、可見性

一個線程對共享變量值的修改,能夠及時地被其他線程看到。

共享變量:如果一個變量在多個線程的工作內存中都存在副本,那么這個變量就是這幾個線程的共享變量。

Java內存模型(JMM):描述了Java程序中各種變量(共享變量)的訪問規則,以及在JVM中將變量存儲到內存和從內存中讀取出變量這樣的底層細節。

2、JMM 基本規則

1)所有的變量都存儲在在主內存中。

2)每個線程都有自己獨立的工作內存,里面保存該線程使用到的變量副本(主內存中該變量的一份拷貝)。

3)線程對共享變量的所有操作都必須在自己的工作內存中進行,不能直接從主內存中讀寫

4)不同線程之間無法直接訪問其他線程工作內存中的變量,線程間變量值的傳遞需要通過主內存來完成。

3、共享變量實現可見性的原理

1)首先在自己線程Thread1里修改共享變量x=1

2)然后更新主內存的x=1

3)其次其他線程Thread2從主內存中讀取x=1,更新自己線程的值,

這樣連續性的操作,可以保證任何一個線程的獨立內存中的共享變量都是最新的值!

4、Java層面實現可見性的方式

1)synchronized

2)volatile

3)concurrent 包

5、synchronized

1)線程解鎖前,必須把共享變量的最新值刷新到主內存中

2)線程加鎖時,將清空工作內存中共享變量的值,從而使用共享變量時需要從主內存中重新讀取最新的值。(注意:加鎖與解鎖需要同一把鎖)

6、synchronized 修飾時,JVM操作的步驟

1)首先獲得互斥鎖

2)清空工作內存

3)從主內存拷貝變量的最新副本到工作內存

4)執行代碼

5)將更改后的共享變量值刷新到主內存

6)釋放互斥鎖

7、重排序

代碼書寫的順序與實際執行的順序不同,指令重排序是編譯器或處理器為了提高程序性能而做的優化!

1)編譯器優化

2)指令優化

3)內存系統優化

最后的結果:有可能導致代碼的執行的順序與編寫順序不一致,但是可以提高CPU性能

8、as-if-serial

無論如何重排序,程序的運行結果都是保持一致的!

單線程中是不能會因為重排序帶來內存可見性的問題。

多線程則會由于重排序帶來共享變量不一致的問題。

9、導致共享變量在線程間不可見的原因

1)線程交叉執行。(原子性來保證)

2)重排序結合線程交叉執行。(原子性來保證)

3)共享變量未及時更新。(內存可見性來保證)

10、synchronized 修飾變量、修飾方法或代碼塊

1)擁有原子性

2)擁有內存可見性

3)重量級

所以他能夠實現線程間執行操作的安全性!

11、volatile 修飾變量

1)不保證原子性

2)擁有可見性

3)輕量級

12、關于 i++

1)首先讀取,從主內存中讀取i的值更新到當前工作內存中

2)其次改變,對i進行加1

3)最后更新,從當前工作內存中的值刷新到主內存中去

所以,這不是一個原子操作,在這個操作過程中勢必會導致線程間交互而導致值的混亂!解決方式就是保證 i++ 具有原子性

1)使用synchronized

2)使用Lock對象,concurrent 包中

Lock lock = new RentrantLock();

try{

? ? lock.lock();

? ? i++

}finally{

? ? lock.unlock();

}

13、volatile 使用場合

1)對變量的寫入操作不依賴其當前值,比如Boolean值,但是 i++ 或 i=i+5

2)該變量沒有包含在其他變量的不變式中,比如: low < high (這里我也不是很清楚)

注意:共享變量都必須是private

final 也實現了內存可見性,因為他的值是不可修改的!

14、結論

對一個共享變量不僅僅要關心他的寫,還關心他的讀,二者都要加鎖;

volatile是輕量級的,能使用,盡量使用!


轉載于:https://my.oschina.net/heweipo/blog/505891

總結

以上是生活随笔為你收集整理的Java 复习 —— JMM基础的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。