java 内存模型
硬件效率与一致性
提高计算的效率
为了提高计算机的计算效率! 我们往往会让计算机并发地执行多个计算任务, 但是这样并不能完全压榨计算机的计算能力! 因为计算机在执行计算任务的时候不只有处理器在单纯计算,处理器还需要与磁盘打交道!进行一些存取数据的操作, 这个IO的时间是非常慢并且是难以消除的,由于计算速度和存储设备的读取写入速度之间存在着几个数量级的差距! 所以便在处理器和内存之间添加了高度缓存来解决处理器等待内存响应的时间!
缓存的作用
添加了缓存之后, 每次都把计算所用到的数据复制到缓存中,让缓存快速运行, 当运算结束后在从缓存中同步到主存!这样处理器就不需要等待缓慢的内存读写了。
缓存带来的问题
通过添加高度缓存能够减少处理器的等待时间,但是也带来了缓存一致性的问题! 在多路处理器的系统中每个处理器都有自己的高度缓存, 他们之间又共享主存, 这样就会出现当多个处理器操作主存中同一个数据的时候出现缓存不一致的情况! 多个处理器同时向主存中同步数据! 这个时候应该使用谁的缓存呢?
缓存一致协议
为了解决缓存一致性的问题, 处理器之间必须遵守缓存一致性的协议!
乱序执行
除了增加高速缓存之外, 为了增加计算单位的使用效率, 处理器可能会对出入的代码进行乱序执行优化! 处理器会在乱序执行之后将计算的结果重组, 来保证该结果和顺序执行的结果是相同的!但是并不会保证程序中语句的执行顺序和代码中的顺序是一致的! 注意: 在java的即时编译器中也会出现类似的指令重排优化!!!
java 内存模型
java 内存模型的目的
关注点
java 内存模型的目的 主要是定义程序中变量的访问规则, 即关注在JVM中变量值存到内存中和从内存中读取变量值这样的底层细节! 此时的变量含义是: 实例字段、静态字段、构成数组对象的元素, 但是不包括局部变量和方法参数, 因为局部变量和方法参数是在虚拟机栈中的私有变量! 不是共享!
主内存
主内存
java 内存模型中规定 java 里面的变量都是存储在 主内存中的! 这里的主内存在物理上是属于虚拟机的一部分!
工作内存
工作内存
出了主内存之外, 每条线程还有自己的工作内存! 线程的工作内存中存放的是当前线程操作主内存变量的副本! 线程对变量的所有操作(读取和赋值)都必须在工作内存中完成! 而不能直接读取主内存中的数据!
注意: 如果一个实例比较大的话, 是不会直接完全复制一份到工作内存中, 而是只复制用到的属性!!!
线程之间怎么相互访问数据
不同线程之间也不能直接访问对方工作内存中的变量, 线程之间的数据访问, 只能通过主内存来进行!
线程、工作内存、主内存关系
主内存主要对应: 堆空间中对象实例数据部分!
工作内存对应: 虚拟机栈的部分!
内存之间的交互
内存之间的交互
-
lock
-
unlock
-
read
-
load
-
user
-
assign
-
store
-
write时编译器中也会出现类似的指令重排优化!!!