It is not difficult to run a program; the difficult thing is how far the program can run! —— a fierce seed
JUC Concurrency Series
JUC Concurrency Series (1): What? I heard that you confuse concurrency and parallel
JUC concurrency series (2): Detailed Condition to achieve accurate notification wakeup
The existence of the lock core is multi-threaded and concurrent, only a thorough understanding of locks, encounter interview do not panic, but also to deal with concurrency issues in practical work with the salary lock to be arbitrary.
1. Who decides the execution order of multiple synchronization methods
Under normal circumstances, the execution order of the two threads is not executed sequentially (from top to bottom), but the existence of a lock. After the same lock is used, they are executed in sequence.
The lock here is the lock of the same object, the lock of the computer object, so whoever is first will execute it first.
Computer computer = new Computer();
1.1 Hand type code implementation
Here we have written two methods (locked two methods, that is, synchronization method), one is learning, the other is playing games.
public class Demo{
public static void main(String[] args) {
Computer computer = new Computer();
new Thread(()->{
computer.study();
},"a").start();
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(()->{
computer.game();
},"b").start();
}
}
class Computer{
public synchronized void study(){
try {
TimeUnit.SECONDS.sleep(5);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("学习");
}
public synchronized void game(){
System.out.println("打游戏");
}
}
operation result
You can see who is in front and who will execute first, so the order is also learn first, then play.
Second, the synchronization method in multiple objects
The execution order of synchronization methods for multiple object locks is still the same, but unlike an object lock, multiple object locks will affect the execution order due to sleep time.
2.1 Hand-knock code implementation
In the above code, we only lock one object, then add another object lock, two objects, and the same two methods. Would you answer that you learn first and then play?
public class Demo{
public static void main(String[] args) {
Computer computer1 = new Computer();
Computer computer2 = new Computer();
new Thread(()->{
computer1.study();
},"a").start();
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(()->{
computer2.game();
},"b").start();
}
}
class Computer{
public synchronized void study(){
try {
TimeUnit.SECONDS.sleep(4);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("学习");
}
public synchronized void game(){
System.out.println("打游戏");
}
}
operation result
The correct answer is: play the game first, then learn.
Three. Synchronous and non-synchronous methods
The difference between the synchronous method and the asynchronous method is that the asynchronous method is not affected by the lock.
3.1 Hand-made code implementation
In the code of 1.1 above, we have added an asynchronous method (ordinary method) for watching movies. We can verify the order of execution.
public void movie(){
System.out.println("看电影");
}
public class Demo{
public static void main(String[] args) {
Computer computer = new Computer();
new Thread(()->{
computer.study();
},"a").start();
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(()->{
computer.game();
},"b").start();
new Thread(()->{
computer.movie();
},"c").start();
}
}
class Computer{
public synchronized void study(){
try {
TimeUnit.SECONDS.sleep(5);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("学习");
}
public synchronized void game(){
System.out.println("打游戏");
}
public void movie(){
System.out.println("看电影");
}
}
operation result
Four, static synchronization method
In the previous article, we talked about the internal classes of Java in a simple way. We talked about static being the first to be executed, and it will be automatically called when the bytecode is loaded, and before the main method main, it is earlier than the construction method. At this time, non-static properties and methods are not yet available. Complete the initialization.
Ultra-detailed in-depth understanding of Java internal classes
The static method is available as soon as the class is loaded, so the locked class itself is the same object.
4.1 Hand-type code implementation
We still create two object locks, but the difference is that our methods have added static to become static methods, let's see the order of execution.
public class Demo{
public static void main(String[] args) {
Computer computer = new Computer();
new Thread(()->{
computer.study();
},"a").start();
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(()->{
computer.game();
},"b").start();
}
}
class Computer{
public static synchronized void study(){
try {
TimeUnit.SECONDS.sleep(5);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("学习");
}
public static synchronized void game(){
System.out.println("打游戏");
}
}
operation result
5. Comparison of static synchronization method and ordinary synchronization method
If you understand the above static synchronization method, I believe you also understand the difference between static synchronization method and ordinary synchronization method.
The static static synchronization method locks the class class, while the normal synchronization method locks the call, so they are two different locks.
After understanding this passage, you also understand the code and the output result.
5.1 Hand code implementation
The following code also creates an object, or two methods, the difference is that the output learning is a static synchronization method, while the output playing game is a normal method, if you can understand
public class Demo{
public static void main(String[] args) {
Computer computer = new Computer();
new Thread(()->{
computer.study();
},"a").start();
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(()->{
computer.game();
},"b").start();
}
}
class Computer{
public static synchronized void study(){
try {
TimeUnit.SECONDS.sleep(5);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("学习");
}
public synchronized void game(){
System.out.println("打游戏");
}
}
operation result
You can see that the static synchronization method and the ordinary synchronization method are two different locks. If there is no sleep, the static synchronization method is executed first, because it is called when the class is loaded (important things, countless times), but However, in the case of sleep delay, our ordinary method is executed first because of the delay;
remember that the static synchronization method and the ordinary method are not the same lock, the former is the class, and the latter is the caller.
Six, finally
At the end, for a better reading experience, I put everything I want to say below, hehe.
I am a seed of decisions based on my will, serious share what I wrote blog has been the same creed.
If you can read this blog post, it means that we are still very destined; I hope it can bring you some help, the creation is not easy, take away the knowledge of my article, your three consecutive leave, like, comment, follow , Is my biggest motivation.