本文是阅读《Java并发编程的艺术》后将自己记忆的理论知识和理解复写出来的产物,若有不足,欢迎指正!
在java中,线程之间是靠共享内存来通信的,是隐式进行的,但对于线程运行顺序的控制(同步),是显示进行的。所以java并发编程和java内存模型有关,java的线程同步需要学习重排序、顺序一致性的知识。
一、java内存模型(JMM)基础
JMM控制了线程和主内存之间的抽象关系,决定一个线程的写入何时对其他线程可见。
1.结构
2.happens-before
happens-before是JMM中两个操作之间的一种关系,一个操作happens-before另一个操作,则前者必须对后者可见,按顺序排在后者之前(但不一定在后者之前执行,可重排序的情况)。happens-before的目的是在保证程序运行结果不变的前提下,尽可能提高程序执行的并行度。
(1)规则
①程序顺序规则:线程中的任意操作 happens-before 该操作的后续
②监视器锁规则:加锁 happens-before 解锁
③volatile变量规则:对一个volatile域的写 happens-before 读
④传递性:A happens-before B, Bhappens-before C, A happens-before C
⑤start()
⑥join()
(2)特点
为程序员提供了强有力的内存可见性保证,对编译器和处理器的约束尽可能少。
二、重排序
编译器和处理器为了优化程序性能而对指令序列进行重新排序的一种手段。但不会对存在数据依赖性(两个操作同时访问一个变量,其中一个操作为写操作,则这两个数据之间存在数据依赖性)的操作做重排序,这是as-if-serial(类似于单线程的happens-before)的语义。
1.类型
2.规则
三、顺序一致性
顺序一致性是指程序的执行结果与在顺序一致性模型中执行的结果相同。
1.顺序一致性模型
保证了内存可见性
(1)一个线程中按程序顺序执行
(2)每个线程看到的操作执行顺序相同,且每个操作原子执行并立刻可见
2.对于未同步顺序的执行特性
(1)最小安全性
保证线程读到的值不会无中生有
(2)不保证和顺序一致性模型运行结果相同
3.与java内存模型差异