目录
内置锁
在Java中,每个对象都有一个内置锁,也称为监视器锁。
内置锁是一种互斥锁,只能被一个线程获得。
当一个线程获取了一个对象的内置锁,其他线程就不能访问这个对象的同步方法或同步代码块,直到锁被释放。
synchronized
java中的2种对象
Java有两种对象:Object实例对象和Class对象。
类锁
使用synchronized关键字修饰static静态方法时,因为静态方法属于Class实例而不是单个Object实例,所以synchronized的同步锁并不是普通Object对象的监视器锁,而是类所对应的Class对象的监视器锁,即类锁。
对象锁
使用被synchronized修饰的普通方法或普通代码块的时候,synchronized的同步锁是当前对象this的监视器锁,即对象锁。
多个synchronized修饰的方法会相互阻塞
在 Java 中,如果一个类中有多个被
synchronized
修饰的方法,那么当一个线程进入其中一个synchronized
方法时,其他线程在尝试进入任何synchronized
方法时都会被阻塞。因为在 Java 中,对象的
synchronized
方法使用的是对象内部的同一把锁(也称为监视器锁)。当一个线程获得了这个对象的锁并进入一个synchronized
方法后,其他线程如果想要进入该对象的任何synchronized
方法,都必须等待当前持有锁的线程释放锁。
public class SyncTest {
synchronized void sync1() {
System.out.println(" 。。。 sync1 start 。。。 ");
ThreadUtil.sleepSeconds(5);
System.out.println(" 。。。 sync1 end 。。。 ");
}
synchronized void sync2() {
System.out.println(" 。。。 sync2 start 。。。 ");
ThreadUtil.sleepSeconds(2);
System.out.println(" 。。。 sync2 end 。。。 ");
}
public static void main(String[] args) {
SyncTest syncTest = new SyncTest();
new Thread(() -> {
for (; ; ) {
syncTest.sync1();
}
}).start();
new Thread(() -> {
for (; ; ) {
syncTest.sync2();
}
}).start();
ThreadUtil.sleepSeconds(1000);
}
}
在这个例子中,sync1和sync2两个方法不会同时运行