Skip to content

Commit 4042e12

Browse files
committed
✨ Introducing new features. volatile
1 parent 2da4989 commit 4042e12

File tree

2 files changed

+69
-0
lines changed

2 files changed

+69
-0
lines changed

MD/concurrent/volatile.md

+29
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,31 @@
11
# 你应该知道的 volatile
22

3+
## 前言
4+
5+
不管是在面试,还是实际开发中 `volatile` 都是一个应该掌握的技能。
6+
7+
首先来看看为什么会出现这个关键字。
8+
9+
## 内存可见性
10+
由于 Java 内存模型(JMM)规定,所有的变量都存放在主内存中,而每个线程都有着自己的工作内存(高速缓存)。
11+
12+
线程在工作时,需要将主内存中的数据拷贝到工作内存中。这样对数据的任何操作都是基于工作内存的(效率提高),不能直接操作主内存以及其他线程工作内存中的数据,之后再将更新之后的数据刷新到主内存中。
13+
14+
> 这里所提到的主内存可以简单认为是**堆内存**,而工作内存则可以认为是**栈内存**
15+
16+
如下图所示:
17+
18+
![](https://ws2.sinaimg.cn/large/006tKfTcly1fmouu3fpokj31ae0osjt1.jpg)
19+
20+
所以在并发运行时会出现线程 B 所读取到的数据是线程 A 更新之前的数据。
21+
22+
显然这肯定是会出问题的,因此 `volatile` 的作用出现了:
23+
24+
> 当一个变量被 `volatile` 修饰时,任何线程对它的写操作都会立即刷新到主内存中,并且会强制让缓存了该变量的线程中的数据清空,必须从主内存重新读取最新数据。
25+
26+
### 内存可见性的应用
27+
28+
29+
## 指令重排
30+
31+
### 指令重排的的应用
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
package com.crossoverjie.concurrent;
2+
3+
import java.util.concurrent.TimeUnit;
4+
5+
/**
6+
* Function:
7+
*
8+
* @author crossoverJie
9+
* Date: 09/03/2018 00:09
10+
* @since JDK 1.8
11+
*/
12+
public class Volatile implements Runnable{
13+
14+
private static volatile boolean flag = true ;
15+
16+
@Override
17+
public void run() {
18+
while (flag){
19+
System.out.println(Thread.currentThread().getName() + "正在运行。。。");
20+
}
21+
System.out.println(Thread.currentThread().getName() +"执行完毕");
22+
}
23+
24+
public static void main(String[] args) throws InterruptedException {
25+
Volatile aVolatile = new Volatile();
26+
new Thread(aVolatile,"thread A").start();
27+
28+
29+
System.out.println("main 线程正在运行") ;
30+
31+
TimeUnit.MILLISECONDS.sleep(100) ;
32+
33+
aVolatile.stopThread();
34+
35+
}
36+
37+
private void stopThread(){
38+
flag = false ;
39+
}
40+
}

0 commit comments

Comments
 (0)