File tree Expand file tree Collapse file tree 2 files changed +69
-0
lines changed
src/main/java/com/crossoverjie/concurrent Expand file tree Collapse file tree 2 files changed +69
-0
lines changed Original file line number Diff line number Diff line change 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 number Diff line number Diff line change 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+ }
You can’t perform that action at this time.
0 commit comments