Java Concurrency the volatile keyword

introduction

When it comes to multi-threading, I think we're the most important thing is to understand the concept of a critical area.

Black question mark .png

For example, a class one girl (critical area), 49 boys (threads), the boys of this goal is a girl, there is a competitive relationship (thread-safety issues). Extended to the actual scene, for example, to add or subtract a number of situations and so on, because there is only one operation object, in a multithreaded environment, it will produce thread-safety issues. Understand the concept of critical areas, we can have a good awareness of multi-threading problems.

Jav memory model (JMM)

Speaking multithreading should look at an abstract diagram of the Java Memory Model (JMM) in the following figure:
JMM.png
thread A and thread B is executed when the will to read shared variables (critical section), and then return to their respective copy local memory, for subsequent operations.
JMM model is a specification, just as Java interfaces. JMM involves three issues: atomicity, visibility, orderly.
The so-called atomic. That is a thread of execution will not be affected by other threads. He is not interrupted. for example:

int i=1

This statement is in Jmm in atomic. Whether it is a thread of execution or multiple threads execute this statement, read out i is equal to 1. What is non-atomicity it stands to reason that if Java code is atomic, should not have threading issues ah. In fact, this is the provision of certain JMM statement is atomic nothing. For examples of non-atoms:

i ++;

The operation of the atom is not. Because he is the inclusion of three operations: reading a first value of i, i is incremented by 1 second, the third assigns the result back to i, the value of i is updated.
The so-called visibility. Visibility means that if a value is changed in the thread A, thread B will immediately know the results.
The so-called orderly. The so-called orderliness orderliness value is semantic. That is the code sequence may vary. Because there is an instruction rearrangement mechanisms. The so-called command reordering, he will change the order of code execution, in order to allow the implementation of more efficient cpu. In order to prevent errors reordering, JMM there happen-before rule which limits execution of those statements the front, that statement is executed after.
Happen-before:
program sequence principles: an inner thread to ensure serializability semantics
volatile principles: write volatile variables occurs before the read
lock rules: first locked then unlock
transitive: a before b, b prior to c, then a c must precede
before the start of each of his operating method thread
all operations before the end of the thread's thread
object's constructor executed before the end of the finalize () method.

volatile

Into the topic, volatile can guarantee visibility and ordering of variables (critical section), but can not guarantee atomicity. for example:

public class VolatileTest implements Runnable{
    private static VolatileTest volatileTest = new VolatileTest();
    private  static volatile int i= 0;
    public static void main(String[] args) throws InterruptedException {
        for (int j = 0; j < 20; j++) {
            Thread a = new Thread(new VolatileTest());
            Thread b = new Thread(new VolatileTest());
            a.start();b.start();
            a.join();b.join();
            System.out.print(i+"&&");
        }

    }
    
    @Override
    public void run() {
        for (int j = 0; j < 1000; j++) {
            i++;
        }
    }

}

// 输出结果
// 2000&&4000&&5852&&7852&&9852&&11852&&13655&&15655&&17655&&19655&&21306     
//&&22566&&24566&&26189&&28189&&30189&&32189&&34189&&36189&&38089&&

The results have seen a problem, although i have added the volatile keyword, description volatile keyword can not guarantee the atomicity of i ++.

What scenarios for the use of the volatile keyword

  1. Lightweight "read - write lock" strategy
private volatile int value;
public int getValue(){ return value;}
public synchronized void doubleValue(){ value = value*value; }

Example 2. Single-mode (dual check locking mechanism

private volatile static Singleton instace;   
public static Singleton getInstance(){  // 没有使用同步方法,而是同步方法块
    //第一次null检查 ,利用volatile的线程间可见性,不需要加锁,性能提高    
    if(instance == null){            
        synchronized(Singleton.class) {    //锁住类对象,阻塞其他线程
            //第二次null检查,以保证不会创建重复的实例       
            if(instance == null){       
                instance = new Singleton(); // 禁止重排序
            }  
        }           
    }  
    return instance;

reference

"Modern Operating Systems (third edition) Chinese version of"
"combat high concurrency Java programming"
"Java concurrent programming art"

If my articles help to you, I can focus on the public micro-channel number, the first time to share your article

MOMlcV.gif

Guess you like

Origin www.cnblogs.com/chenzhuantou/p/11932915.html