java内存模型

什么是java内存模型:

首先明确JMM是一种规范
目的解决由于多线程通过共享内存进行通信时,存在的本地内存数据不一致、编译器对代码指令重排序、处理器对代码乱序执行等带来的问题。从而保证并发编程场景中的原子性、可见性和有序性

**原子性:**原子性指的是一个操作不可中断,即使是在多线程环境下,一个操作一旦开始就不会被其他线程影响。

**可见性:**可见性就是指当一个线程修改了线程共享变量的值,其它线程能够立即得知这个修改。

**有序性:**即程序执行的顺序按照代码的先后顺序执行(但是在JMM的指令重排后程序的执行顺序可能会变,但是保证最终执行的结果会和代码顺序执行结果一致)。

Java线程与内存模型的关系(引用:<<并发编程的艺术>>):

Java线程之间的通信由Java内存模型(JMM)控制,JMM决定一个线程对共享变量的写入何时对另一个线程可见。从抽象的角度来看,JMM定义了线程和主内存之间的抽象关系:线程之间的共享变量存储在主内存(Main Memory)中,每个线程都有一个私有的本地内存(Local Memory),本地内存中存储了该线程以读/写共享变量的副本。本地内存是JMM的一个抽象概念,并不真实存在。它涵盖了缓存、写缓冲区、寄存器以及其他的硬件和编译器优化。

参考下图理解:
在这里插入图片描述

Ps:java内存模型规定所有变量都存储在主内存

JMM为保证原子性 一致性 可见性的实现方法:

解决原子性问题:
除了JVM(Java虚拟机)自身提供的对基本数据类型读写操作的原子性外,对于方法级别或者代码块级别的原子性操作,可以使用synchronized关键字或者重入锁**(ReentrantLock)**保证程序执行的原子性

解决可见性问题:
可以使用synchronized关键字或者volatile关键字解决,它们都可以使一个线程修改后的变量立即对其他线程可见

有序性:
可以利用volatile关键字解决,因为volatile的另外一个作用就是禁止重排序优化,而synchronized则是有一个变量在同一时刻只允许一条线程对其进行lock操作获得有序性,这条规则决定了持有同一个锁的两个同步块只能串行地进入。

补充:
happens-before原则(JMM的辅助)保证多线程环境下两个操作间的原子性、可见性以及有序性。
1、程序顺序原则:
即在一个线程内必须保证语义串行性,也就是说按照代码顺序执行;
2、锁规则:
解锁(unlock)操作必然发生在后续的同一个锁的加锁(lock)之前。也就是说,如果对于一个锁解锁后,再加锁,那么加锁的动作必须在解锁动作之后(同一个锁);
3、volatile规则:
volatile变量的“写”先发生于“读”,这保证了volatile变量的可见性。简单的理解就是:volatile变量在每次被线程访问时,都强迫从主内存中读该变量的值;而当该变量值发生变化时,又会强迫将最新的值刷新到主内存中。因此,任何时刻,不同的线程总是能够看到该变量的最新值;
4、线程启动规则
线程的start()方法先于它的每一个动作,即如果线程A在执行线程B的start方法之前修改了共享变量的值,那么当线程B执行start方法时,线程A对共享变量的修改对线程B是可见的;
5、传递性:
A先于B ,B先于C ,那么A必然先于C;
6、线程终止规则:
线程的所有操作先于线程的终结,Thread.join()方法的作用是等待当前执行的线程终止。假设在线程B终止之前,修改了共享变量,线程A从线程B的join方法成功返回后,线程B对共享变量的修改将对线程A可见。
7、线程中断规则:
对线程 interrupt() 方法的调用先行发生于被中断线程的代码检测到中断事件的发生,可以通过Thread.interrupted()方法检测线程是否中断。
8、对象终结规则:
对象的构造函数执行(对象的初始化),结束先于finalize()方法;

上述8条原则无需手动添加同步手段(synchronized ||volatile)即可实现上述效果,也就是在多线程种默认遵守该规则

初识JMM(小总结)

引用文章:
https://blog.csdn.net/pcwl1206/article/details/84871090
https://www.cnblogs.com/54chensongxia/p/12022648.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值