JMM的理解学习

网友投稿 671 2022-05-30

1.JMM的定义

JMM是JAVA 的内存模型(java memory model),不存在的东西,是一种概念或者约定,规定了内存主要划分为主内存和工作内存两种。而所规定的主内存和工作内存跟JVM内存划分(堆、栈、方法区)是在不同的层次上进行的,但是用类比的方法可以将主内存类比为Java堆中的对象实例部分,工作内存类比为栈中的部分区域,从更底层的来说,主内存对应的是硬件的物理内存,工作内存对应的则是寄存器和高速缓存

为什么我们要定义这么一个规则呢?是因为在不同的硬件生产商和不同的操作系统下,内存的访问逻辑是有一定的差异的,即当代码在某个系统环境下运行正常并且线程安全,但是换了个系统就出现了各种的问题。Java内存模型(JMM)应就这样运而生,为了屏蔽系统和硬件的差异,让一套代码在不同平台下能到达相同的访问结果。

2.关于JMM的同步约定

2.1线程解锁前

必须把共享变量立刻刷回主内存(因为线程在处理变量的时候是,复制了一份在自己的线程的工作内存中进行处理,此处意思是将自己线程中的变量立刻刷回主存中,让线程的工作内存中和主存中的变量保持一致)

2.2 线程加锁前

必须读取主内存中的最新值更新到工作内存中,也是为了让工作内存中的变量和线程中保持一致。

2.3 加锁和解锁是必须同一把锁(不是同一把锁的话,大家就各玩各的了,没办法一块愉快玩耍了)。

3.JMM的八种交互操作

JMM交互操作共有8种(在主存和工作内存之间进行的操作)并且虚拟机实现必须保证每一个操作都是原子的,不可在分的。方法如下:

3.1 lock

加锁操作,作用于主内存的变量,把一个变量标识为线程独占状态;

3.2 unlock

解锁操作,作用于主内存的变量,把一个处于锁定状态的变量释放出来,释放后的变量才能被其他线程锁定;

3.3 read

从主存中读取操作,作用于主内存变量,把一个变量的值从主内存读取到线程的工作内存中,以便随后的load动作使用;

3.4 load

将主存中读取的数据写入工作内存的加载写入操作,作用于工作内存的变量,把read操作读取的变量从主存中放入工作内存中;

3.5 use

执行引擎使用加载到工作内存中的数据的操作,作用于工作内存中的变量,把工作内存中的变量传输给执行引擎,当虚拟机遇到需要使用到变量的值就会使用这个指令;

3.6 assign

执行引擎将use使用操作后的数据再赋值回工作内存的赋值操作,作用于工作内存中的变量,把从执行引擎中接受到的值放入工作内存的变量副本中;

3.7 store

将assign赋值到工作内存后进行的读取操作(准备再写入到主内存中),作用于主内存中的变量,把从工作内存中变量的值传送到主内存中,以便后续的write操作使用;

3.8 write

将从工作内存中通过store读取操作读取的数据写入到主内存的写入操作,作用于主内存中的变量,把store操作从工作内存中得到的变量的值放入主内存的变量中;

4.JMM对这八种操作的使用制定的规则

JMM的理解学习

4.1 不允许read和load、store和write操作之一单独出现,必须成双成对不能分开~

4.2 不允许线程丢弃其最近的assign操作,即工作内存中的变量数据发生改变之后必须告知主内存;

4.3 不允许线程将没有assign操作的数据从工作内存同步回主内存;

4.4 不允许工作内存直接使用一个未被初始化的变量,新的变量必须在主内存中诞生,即use操作之前必须经过load操作或者或者store操作之前必须经过assign操作;

4.5 一个变量同一时间只有一个线程能对其进行lock加锁操作,多次lock加锁操作后,必须执行相同次数的unlock解锁操作才能解锁;

4.6 如果对一个变量进行lock操作,会清空所有工作内存中此变量的值,在执行引擎使用这个变量前,必须重新load或assign操作初始化变量的值;

4.7 如果一个变量没有被lock加锁操作,就不能对其进行unlock解锁操作,也不能unlock解锁一个被其他线程加锁操作锁住的变量;

4.8 对一个变量进行unlock解锁操作之前,必须把此变量同步回主内存;

版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:华为云获TISAX认证,保障汽车行业客户安全上云
下一篇:jsp之四种范围对象
相关文章