


Java introduces eight locks to help you thoroughly understand object locks and class locks
Related free learning recommendations: java basic tutorial
8 Lock problem demonstration
1. Standard access
/*手机类可以发邮件和发短信*/class Phone{ public synchronized void sendEmail() throws Exception{ System.out.println("***sendEmail"); } public synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { phone.sendSMS(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
Standard access, print email or text message first.
It doesn’t matter who is printed first. It depends on the execution of the CPU. It is the main thread that activates them. I don't know who will be scheduled first later.
In order to ensure the effect, we add thread.sleep(100) between the codes of A and B. At this time, we can ensure that A is printed first.
Explanation:
As long as there is a resource class, no matter how many synchronization methods it has, as long as a thread first accesses any synchronization method in the resource class, then it will not lock this method. is the entire resource class where the method is located. In other words, what is locked is the object. What it locks is not the current method.
In other words, these synchoronized methods all belong to the same resource class, and the entire resource class is locked.
2. Pause for 4 seconds in the email method. Please print the email or text message first.
/*手机类可以发邮件和发短信*/class Phone{ public synchronized void sendEmail() throws Exception{ TimeUnit.SECONDS.sleep(4); //表示暂停4秒,它是一个枚举类型 System.out.println("***sendEmail"); } public synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { phone.sendSMS(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
Print the email first. The phone object lock obtained by the synchronization method will not be released by sleep. It will be executed immediately when the time comes. So print the email method first
Explanation:
It is similar to question 1.
As long as there is a resource class, no matter how many synchronization methods it has, as long as a thread first accesses any synchronization method in the resource class, it will not lock this method, but the method. The entire resource class. In other words, what is locked is the object. What it locks is not the current method.
For example: The monitor and I need to use the same mobile phone to make a call. I must wait for the monitor to finish the call before I can continue the call. The monitor was disconnected for a while while he was using it, so I could only wait for the monitor to finish.
3. Add the ordinary sayHello method. Please print the email first or hello
Print hello first
/*手机类可以发邮件和发短信*/class Phone{ public synchronized void sendEmail() throws Exception{ TimeUnit.SECONDS.sleep(4); //表示暂停4秒,它是一个枚举类型 System.out.println("***sendEmail"); } public synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); } public void sayHello(){ System.out.println("***sayHello"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { //phone.sendSMS(); phone.sayHello(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
Explanation: After adding a common method, it was found that it has nothing to do with synchronization lock. Therefore it does not need to wait for the synchronization lock to be released.
Here is an example. The monitor used his cell phone to make a call. And I want to borrow a mobile phone charging cable from the squad leader. The two are not mutually exclusive, so I can borrow the charging cable before the squad leader finishes calling.
4. Two mobile phones, please print the email or text message first
/*手机类可以发邮件和发短信*/class Phone{ public synchronized void sendEmail() throws Exception{ TimeUnit.SECONDS.sleep(4); //表示暂停4秒,它是一个枚举类型 System.out.println("***sendEmail"); } public synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); } public void sayHello(){ System.out.println("***sayHello"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); Phone phone2=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { //phone.sendSMS(); //phone.sayHello(); phone2.sendSMS(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
Explanation: Here is an example. The monitor uses Its mobile phone law mail. I called on my own cell phone. Then it doesn't matter who comes first and who comes last.
5. Two static synchronization methods, the same mobile phone, please print the email or text message first
/*手机类可以发邮件和发短信*/class Phone{ public static synchronized void sendEmail() throws Exception{ TimeUnit.SECONDS.sleep(4); //表示暂停4秒,它是一个枚举类型 System.out.println("***sendEmail"); } public static synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); } public void sayHello(){ System.out.println("***sayHello"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); Phone phone2=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { phone.sendSMS(); //phone.sayHello(); //phone2.sendSMS(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
Explanation: It can be combined with question 6 Analysis
6. Two static synchronization methods, two mobile phones, please print the email or text message first
/*手机类可以发邮件和发短信*/class Phone{ public static synchronized void sendEmail() throws Exception{ TimeUnit.SECONDS.sleep(4); //表示暂停4秒,它是一个枚举类型 System.out.println("***sendEmail"); } public static synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); } public void sayHello(){ System.out.println("***sayHello"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); Phone phone2=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { //phone.sendSMS(); //phone.sayHello(); phone2.sendSMS(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
Analysis:
static Belongs to a class. In other words, he does not belong to an independent individual of the current object this. It is a global class. This requires considering the difference between object locks and global locks. Global locks are class locks. At this time, whether it is one phone or multiple phones, they all come from the same Phone class. No matter which object you lock now, I have to wait until it releases the lock before it can be used.
7.1 static synchronization method, 1 ordinary synchronization method, the same mobile phone, please print the email or text message first
/*手机类可以发邮件和发短信*/class Phone{ public static synchronized void sendEmail() throws Exception{ TimeUnit.SECONDS.sleep(4); //表示暂停4秒,它是一个枚举类型 System.out.println("***sendEmail"); } public synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); } public void sayHello(){ System.out.println("***sayHello"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); Phone phone2=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { phone.sendSMS(); //phone.sayHello(); //phone2.sendSMS(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
One static, An ordinary one. The same phone is locked. The static method locks the Class. It is equivalent to us locking one school gate and one is an ordinary synchronization method, which locks the current object. For example, ordinary teachers. The objects of the lock are different. No conflict
8.1 static synchronization method, 1 normal synchronization method, two mobile phones, please print the email or text message first
/*手机类可以发邮件和发短信*/class Phone{ public static synchronized void sendEmail() throws Exception{ TimeUnit.SECONDS.sleep(4); //表示暂停4秒,它是一个枚举类型 System.out.println("***sendEmail"); } public synchronized void sendSMS() throws Exception{ System.out.println("***sendSMS"); } public void sayHello(){ System.out.println("***sayHello"); }}public class Lock8Demo { public static void main(String[] args) throws InterruptedException { //创建一个资源类 Phone phone=new Phone(); Phone phone2=new Phone(); new Thread(()->{ try { phone.sendEmail(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"A").start(); Thread.sleep(100); new Thread(()->{ try { //phone.sendSMS(); //phone.sayHello(); phone2.sendSMS(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } },"B").start(); }}
Explanation: This is the same as above.
8 Lock Theory Explanation
1. If there are multiple synchronized methods in an object, as long as one thread calls one of the synchronized methods at a certain time, other threads can only wait. In other words, at a certain time, Only one thread can access these synchronized methods.
The current object this is locked. After being locked, other threads cannot enter other synchronized methods of the current object.
After adding a normal method, I found that it has nothing to do with the synchronization lock.
After exchanging the two objects, they no longer have the same lock, and the situation changes immediately.
After switching to static synchronization methods, the situation immediately changed
All non-static synchronization methods use the same lock ------ the instance object itself
2.synchronized realizes synchronization The basis of: Every object in Java can be used as a lock.
Specifically manifested in the following three forms:
- For ordinary synchronization methods, the lock is the current instance object
- For synchronization method blocks, the lock is the object configured in synchronized brackets.
For example, write
synchronized(this){
} - in the method. For static synchronization methods, the lock is the Class object of the current class.
When a process attempts to access a synchronized code block, it must first obtain the lock. Exiting or throwing an exception must release the lock.
That is to say, after the non-static synchronization method of an instance object acquires the lock, other non-static synchronization methods of the instance object must wait for the method that acquired the lock to release the lock before they can acquire the lock. However, because the non-static synchronization methods of other instance objects use different locks from the non-static synchronization methods of the instance object, they can acquire their own locks without waiting for the non-static synchronization method of the instance object that has acquired the lock to release the lock. .
All static synchronization methods also use the same lock-----the class object itself.
The two locks are two different objects, so there will be no race conditions between static synchronization methods and non-static synchronization methods. (Issue 78). That is, one lock class and one lock this, the two do not conflict.
But once a static synchronization method acquires the lock, other static synchronization methods must wait for the method to release the lock before they can acquire the lock. Regardless of whether it is between static methods of the same instance object or between static synchronization methods of different instance objects, as long as they are instance objects of the same class. (Question 56)
The above is the detailed content of Java introduces eight locks to help you thoroughly understand object locks and class locks. For more information, please follow other related articles on the PHP Chinese website!

Hot AI Tools

Undresser.AI Undress
AI-powered app for creating realistic nude photos

AI Clothes Remover
Online AI tool for removing clothes from photos.

Undress AI Tool
Undress images for free

Clothoff.io
AI clothes remover

Video Face Swap
Swap faces in any video effortlessly with our completely free AI face swap tool!

Hot Article

Hot Tools

Notepad++7.3.1
Easy-to-use and free code editor

SublimeText3 Chinese version
Chinese version, very easy to use

Zend Studio 13.0.1
Powerful PHP integrated development environment

Dreamweaver CS6
Visual web development tools

SublimeText3 Mac version
God-level code editing software (SublimeText3)

Hot Topics











Java 8 introduces the Stream API, providing a powerful and expressive way to process data collections. However, a common question when using Stream is: How to break or return from a forEach operation? Traditional loops allow for early interruption or return, but Stream's forEach method does not directly support this method. This article will explain the reasons and explore alternative methods for implementing premature termination in Stream processing systems. Further reading: Java Stream API improvements Understand Stream forEach The forEach method is a terminal operation that performs one operation on each element in the Stream. Its design intention is

PHP is a scripting language widely used on the server side, especially suitable for web development. 1.PHP can embed HTML, process HTTP requests and responses, and supports a variety of databases. 2.PHP is used to generate dynamic web content, process form data, access databases, etc., with strong community support and open source resources. 3. PHP is an interpreted language, and the execution process includes lexical analysis, grammatical analysis, compilation and execution. 4.PHP can be combined with MySQL for advanced applications such as user registration systems. 5. When debugging PHP, you can use functions such as error_reporting() and var_dump(). 6. Optimize PHP code to use caching mechanisms, optimize database queries and use built-in functions. 7

PHP and Python each have their own advantages, and the choice should be based on project requirements. 1.PHP is suitable for web development, with simple syntax and high execution efficiency. 2. Python is suitable for data science and machine learning, with concise syntax and rich libraries.

PHP is suitable for web development, especially in rapid development and processing dynamic content, but is not good at data science and enterprise-level applications. Compared with Python, PHP has more advantages in web development, but is not as good as Python in the field of data science; compared with Java, PHP performs worse in enterprise-level applications, but is more flexible in web development; compared with JavaScript, PHP is more concise in back-end development, but is not as good as JavaScript in front-end development.

PHP and Python each have their own advantages and are suitable for different scenarios. 1.PHP is suitable for web development and provides built-in web servers and rich function libraries. 2. Python is suitable for data science and machine learning, with concise syntax and a powerful standard library. When choosing, it should be decided based on project requirements.

PHPhassignificantlyimpactedwebdevelopmentandextendsbeyondit.1)ItpowersmajorplatformslikeWordPressandexcelsindatabaseinteractions.2)PHP'sadaptabilityallowsittoscaleforlargeapplicationsusingframeworkslikeLaravel.3)Beyondweb,PHPisusedincommand-linescrip

Capsules are three-dimensional geometric figures, composed of a cylinder and a hemisphere at both ends. The volume of the capsule can be calculated by adding the volume of the cylinder and the volume of the hemisphere at both ends. This tutorial will discuss how to calculate the volume of a given capsule in Java using different methods. Capsule volume formula The formula for capsule volume is as follows: Capsule volume = Cylindrical volume Volume Two hemisphere volume in, r: The radius of the hemisphere. h: The height of the cylinder (excluding the hemisphere). Example 1 enter Radius = 5 units Height = 10 units Output Volume = 1570.8 cubic units explain Calculate volume using formula: Volume = π × r2 × h (4

The reasons why PHP is the preferred technology stack for many websites include its ease of use, strong community support, and widespread use. 1) Easy to learn and use, suitable for beginners. 2) Have a huge developer community and rich resources. 3) Widely used in WordPress, Drupal and other platforms. 4) Integrate tightly with web servers to simplify development deployment.
