1. 程式人生 > >並行程式設計之Java記憶體模式

並行程式設計之Java記憶體模式

Java記憶體模式

以前我在看一些並行程式設計的書時候,老是有些模糊,後來看到《深入理解Java虛擬機器 第二版》這邊書在並行哪章時候,才逐漸清晰,現在就來講講Java記憶體模式。
- 主存和工作記憶體
1. 主存 儲存了有關物件class屬性欄位,全域性變數等資訊
2. 工作記憶體指執行緒相關儲存資訊。
一般來說,工作記憶體會得到主存中的一部分記憶體資訊拷貝,當工作記憶體更新了某些變數值得時候必須要回寫到主存中。

這裡寫圖片描述

  • 主存和工作記憶體互動操作
    1. lock 作用於主存記憶體變數,它把一個變數標識為一條執行緒獨佔的狀態
    2. unlock 作用於主存記憶體變數,他把處於鎖定的變數釋放出來,釋放後的變數可以被其他執行緒鎖定
    3. read 作用於主存記憶體變數,把變數讀到工作記憶體中,一般load使用
    4. load 作用於工作記憶體變數,把read的操作的變數放入工作記憶體變數副本中
    5. use 作用於工作記憶體存變數,把變數傳給執行引擎,每當虛擬機器遇到一個需要使用到變數的值得位元組碼指令時候就好執行這個操作
    6. assign賦值,作用於工作記憶體。它把一個從執行引擎接收的賦值給工作記憶體的變數,每當虛擬機器遇到一個給變數賦值的位元組碼指令時執行這個操作
    7. store 作用於工作記憶體,它把一個變數從工作記憶體中傳送到主記憶體中,以便隨後write操作
    8. write 作用於主記憶體變數,把store的從工作記憶體中得到變數的值放到主記憶體的變數中去

需要注意的將一個變數從主存到工作記憶體,需要順序執行read->load stroe->write操作。也就是說,read與Load,store與write之間可以插入其他指令,如果需要訪問變數a,b,一種可能是順序read a,read b,load b,load a 。

八個操作的規則有一下八種規則:
1. 不允許 read 和 load、 store 和write操作單獨出現
2. 不允許一個執行緒丟棄它的最近assign操作即變數在工作記憶體中改變了之後必須把該變化同步回主記憶體
3. 不允許執行緒無原因(沒有發生過如何assign操作)地把資料從執行緒的工作記憶體同步主記憶體中
4. 一個新的變數只能在主記憶體”誕生”.不允許在工作記憶體中直接使用一個未被初始化(load或assign)的變數,換句話說,就是一個變數實施use、store操作之前,必須先執行過了assign和load操作
5. 一個變數同一時刻只能被一條執行緒lock,並且可以同時多次lock,進行多少次lock必須unlock多少次,變數才會被解鎖
6. 如果對一個變數執行lock操作,那將會清空工作記憶體中此變數的值,在執行引擎使用這個變數前,需要重新執行load或assign操作初始化變數的值
7. 如果一個變數先沒有被Lock操作鎖定,那就不允許對它unlock操作,也不允許去unlock一個被其它執行緒鎖定的變數
8. 對一個變數執行unlock操作之前,必須先把此變數同步回主存中(執行store、write操作)
摘自《深入理解Java虛擬機器 第二版》
下一篇,判斷程式碼是否併發的先行發生原則。

相關推薦

並行程式設計Java記憶體模式

Java記憶體模式 以前我在看一些並行程式設計的書時候,老是有些模糊,後來看到《深入理解Java虛擬機器 第二版》這邊書在並行哪章時候,才逐漸清晰,現在就來講講Java記憶體模式。 - 主存和工作記憶體 1. 主存 儲存了有關物件class屬性欄位,全

實戰Java高併發程式設計Java記憶體模型和執行緒安全

Java記憶體模型 原子性: 是指一個操作是不可中斷的.即使多個執行緒一起執行的時候,一個操作一旦開始,就不會被其他執行緒干擾. 一般CPU的指令是原子的. Q:i++是原子操作嗎? A:不是.

併發程式設計Java記憶體模型

  在介紹Java記憶體模型之前,先來了解一下為什麼要有記憶體模型,以及記憶體模型是什麼。然後我們基於對記憶體模型的瞭解,學習Java記憶體模型以及併發程式設計的三大特性。   為什麼要有記憶體模型   在計算機中,所有的運算操作都是由CPU的暫存器來完成的,CPU指令的執行需要涉及到資料的讀

JVM學習java記憶體模型

JVM學習之java記憶體模型 以下blog內容來自《深入理解Java虛擬機器_JVM高階特性與最佳實踐》感謝作者!! java虛擬機器規範定義了一種java記憶體模型(JMM)來遮蔽不同硬體和作業系統的差異,達到跨平臺執行效果,記憶體模型的定義一個宗旨就是併發記憶體訪問操作不會產生

程式設計單例模式VS靜態方法

原文:https://blog.csdn.net/johnny901114/article/details/11969015?utm_source=copy  我們在設計程式經常會有這種需求 , 某個類裡的方法能夠全域性訪問. 在這種情況下有兩種實現方案 :  1>

jvm學習java記憶體區域

java虛擬機器在執行java程式的過程中會把它所管理的記憶體劃分為若干不同區域:有些是依賴使用者執行緒的啟動和結束而建立和銷燬的,有的則是隨著虛擬機器程序的啟動而存在。 執行緒共享區域:方法區 、堆。 執行緒隔離(各個執行緒獨有區域)虛擬機器棧、本地方法棧、程式計數器。  

理解JVMJava記憶體區域

Java虛擬機器執行時資料區分為以下幾個部分: 方法區、虛擬機器棧、本地方法棧、堆、程式計數器。如下圖所示: 程式計數器 程式計數器可看作當前執行緒所執行的位元組碼行號指示器,位元組碼直譯器工作時就是通過改變這個計數器的值來選取下一條需要執行的位元組碼指令。Java虛擬機器的多執行緒是通過執行緒輪流切換

Java 多執行緒(六)Java記憶體模型

1. 併發程式設計的兩個問題 在併發程式設計中, 需要處理兩個關鍵問題: 執行緒之間如何通訊及執行緒之間如何同步 通訊指的是執行緒之間是以何種機制來交換資訊, 在指令式程式設計中, 執行緒之間的通訊機制有兩種:共享記憶體和訊息傳遞。在共享記憶體的模型中, 執行緒之間共享程式的公共狀態, 通過讀寫記憶體中的

深入理解Java虛擬機器(七)Java記憶體模型

深入理解Java虛擬機器系列文章 Java記憶體模型規定了所有的變數都儲存在主記憶體,每個執行緒都有自己的工作記憶體,執行緒中的工作記憶體儲存了被該執行緒使用到的變數的主記憶體的副本拷貝。執行緒對變

JVMJava記憶體結構

Java記憶體結構的幾大部分如下圖: 接下來,會對上面每部分割槽域的功能一一解釋。 1、程式計數器:是執行緒私有區,是記憶體中一塊較小的區域,是當前執行緒執行的位元組碼指令的行號指示器,如果執行緒執行的是Java方法,程式計數器記錄的是正在執行的虛擬機器位元組碼指令的地址,如果執行的是native方法

JVM---Java記憶體分配引數

引數總結 配置 說明 -Xms 設定初始堆記憶體大小 -Xmx 設定堆記憶體的最大值 -Xss 設定棧記憶體的大小

VolatileJava記憶體模型概念

本文主要講解Java記憶體模型和併發的基礎概念,目的是為下文“volatile實踐”一文做鋪墊。 1.記憶體模型相關概念   大家都知道,計算機在執行程式時,每條指令都是在CPU中執行的,而執行指令過程中,勢必涉及到資料的讀取和寫入。由於程式執行過程中的臨時資料是存放在主存(實體記憶體)當中的,這時就存在

Java例項學習 Java併發程式設計java.util.concurrent.CopyOnWriteArrayList

CopyOnWriteArrayList   CopyOnWriteArrayList是ArrayList在併發環境下的替代品。CopyOnWriteArrayList通過增加寫時複製語義來避免併發訪問引起的問題,也就是說任何修改操作都會在底層建立一個列表的副本,也就意

Java例項學習 Java併發程式設計java.util.concurrent.CountDownLatch

import java.util.concurrent.CountDownLatch; /**  * 工人類  */ class Worker {     private String name;        // 名字     private long workDuration;  // 工作持續時間  

idea外掛篇java記憶體分析工具(JProfiler)

前言 在執行java的時候有時候想測試雲執行時佔用記憶體情況,這時候就需要使用測試工具查看了。在eclipse裡面有 Eclipse Memory Analyzer tool(MAT)外掛可以測試,而

Java記憶體模式

public class VectorMemoryLeak {    public static void main(String args[]){        Vector<String> vector = new Vector<String>();        for( int

Linux環境程式設計共享記憶體區(一):共享記憶體區簡介

共享記憶體區是可用IPC形式中最快的。一旦記憶體區對映到共享它的程序的地址空間,程序間資料的傳遞就不再涉及核心。然而往該共享記憶體區存放資訊或從中取走資訊的程序間通常需要某種形式的同步。不再涉及核心是指:程序不再通過執行任何進入核心的系統呼叫來彼此傳遞資料。核心必須建立允許

並行程式設計條件變數(posix condition variables)

在整理Java LockSupport.park()的東東,看到了個"Spurious wakeup",重新梳理下。 首先來個《UNIX環境高階程式設計》裡的例子: #include <pthread.h> struct msg { struct msg *

【CUDA並行程式設計四】矩陣相乘

前面介紹了基本的Cuda程式設計的相關知識,那麼這一篇在此基礎之上來看看GPU在處理資料計算上的高效能,我們拿矩陣相乘來作為例子。 1.CPU上執行矩陣相乘以及效能。 在CPU上進行矩陣相乘運算的程式碼: mat_mul.cc: //a[i]*b[i] + c[i] =

後端程式設計JAVA面向切面的程式設計

        很久沒寫文章了,因為圍繞這個內容錄了視訊,視訊裡基於提綱做了很多擴充套件,所以本文也只是把大綱貼出來,沒有詳細展開,具體還是請看視訊吧【youku畫面太垃圾了,我已在YOUKU上刪除,上載到了網盤上】:   視訊地址:   ++++++++++++++++