Java multithreading technology - Volatile keyword parsing

Keywords: Java

Analyzing volatile keyword can analyze from these three aspects: what is the atomicity of the program, what is the visibility of the program, and what is the order of the program

What is the atomicity of program

Which of the following statements are atomic operations?

public class ThreadCounter implements Runnable {
      private int count = 0;
      @Override
      public void run() {
            ++count;
//          count++;
      }
      public static void main(String[] args) throws InterruptedException {
            ThreadCounter thread = new ThreadCounter();
            for(int i = 0; i< 10000; i++){
                  new Thread(thread).start();
            }
            Thread.sleep(1000);//Make sure the thread is finished
            System.out.println(thread.count);
      }
}

Demonstration results: Statements 1 and 2 are non atomic operations, statements 3 and 4 are atomic operations

Execute instruction: javap -s -c ThreadCounter
run method's script (count + +):
 
count + + is a line of code divided into four instructions, which are inconsistent in the case of multithreading.

Solution:

public class ThreadCounter implements Runnable {
      private int count = 0;
      @Override
      public void run() {
            synchronized (this) {
                  ++count;
            //    count++;
            }
      }
      public static void main(String[] args) throws InterruptedException {
            ThreadCounter thread = new ThreadCounter();
            for(int i = 0; i< 10000; i++){
                  new Thread(thread).start();
            }
            Thread.sleep(1000);//Make sure the thread is finished
            System.out.println(thread.count);
      }
}

What is program visibility?

 

public class VolatileExample {
      boolean v =false;
      
      private void write(){
            v =true;
      }
      
      private void read(){
            while(!v){
            }
            System.out.println("End of program!");
      }
      
      public static void main(String[] args) throws InterruptedException {
            final VolatileExample example = new VolatileExample();
            Thread thread1 = new Thread(()->{example.read();});
            thread1.start();
            Thread.sleep(1000);
            Thread thread2 = new Thread(()->{example.write();});
            thread2.start();
      }
}
Results:
The program does not end, and the v in the read method does not exit the loop due to the modification of the write method!
Solution: add volatile keyword to variable v
public class VolatileExample {
      volatile boolean v =false;
      
      private void write(){
            v =true;
      }
      
      private void read(){
            while(!v){
            }
            System.out.println("End of program!");
      }
      
      public static void main(String[] args) throws InterruptedException {
            final VolatileExample example = new VolatileExample();
            Thread thread1 = new Thread(()->{example.read();});
            thread1.start();
            Thread.sleep(1000);
            Thread thread2 = new Thread(()->{example.write();});
            thread2.start();
      }
}

What is the order of procedure?

 

Volatile application scenario

1. Status tag quantity
 
public class ThreadTest {
      private volatile boolean isContinue = false;
      
      private class HandleThread extends Thread {
            @Override
            public void run() {
                  while (isContinue) {
                        // do something
                  }
            };
      }
}

2. double check 

 

 

Summary:

volatile can play a role in visibility and order, but it can not guarantee atomicity. It is a kind of weak synchronization.

synchronized can ensure atomicity, visibility and consistency. It is a strong synchronization.

Posted by dsandif on Sun, 03 May 2020 19:46:26 -0700