当线程在 Java 中进入同步块/方法时到底发生了什么
What exactly happens when thread enters a synchronized block / method in Java
我很好奇当我的线程到达同步块并阻塞监视器时到底发生了什么。
它实际上是否在尝试使用此监视器的所有其他线程上隐式调用 wait()?或者监视器有一些正在更改的特定标志?
另外,当我们跳出同步块时会发生什么?它会以某种方式为当前监视器调用 notify 或 notifyAll 吗?
我真的很纠结这个
我认为最好从底层同步原语的角度来思考:java 监视器是一个互斥量,同步块是互斥量在 {
上锁定并解锁的区域}
wait、notify 和 notifyAll 是在与互斥体关联的条件变量上调用的方法。
要记住的重要一点是,当调用 wait()
时,互斥量可以在同步块中解锁,因为 wait 将解锁互斥量并阻塞,直到通知或notifyAll 被调用.
因此,尽管推断这是不可能的,但多个线程仍然可以在同步块中被阻塞。
更新:带注释的代码演示了这一点:
Object lock;
// ...
synchronized (lock) { // Underlying mutex is locked.
// ...
lock.wait(); // Unlocks mutex, blocks until notify, relocks mutex
// ...
} // Underlying mutex unlocked
一旦lock.wait()
被调用,其他线程可以自由进入同步块。它们也会阻塞,直到 lock.notify()
或 lock.notifyAll()
唤醒它们。
我很好奇当我的线程到达同步块并阻塞监视器时到底发生了什么。
它实际上是否在尝试使用此监视器的所有其他线程上隐式调用 wait()?或者监视器有一些正在更改的特定标志?
另外,当我们跳出同步块时会发生什么?它会以某种方式为当前监视器调用 notify 或 notifyAll 吗?
我真的很纠结这个
我认为最好从底层同步原语的角度来思考:java 监视器是一个互斥量,同步块是互斥量在 {
上锁定并解锁的区域}
wait、notify 和 notifyAll 是在与互斥体关联的条件变量上调用的方法。
要记住的重要一点是,当调用 wait()
时,互斥量可以在同步块中解锁,因为 wait 将解锁互斥量并阻塞,直到通知或notifyAll 被调用.
因此,尽管推断这是不可能的,但多个线程仍然可以在同步块中被阻塞。
更新:带注释的代码演示了这一点:
Object lock;
// ...
synchronized (lock) { // Underlying mutex is locked.
// ...
lock.wait(); // Unlocks mutex, blocks until notify, relocks mutex
// ...
} // Underlying mutex unlocked
一旦lock.wait()
被调用,其他线程可以自由进入同步块。它们也会阻塞,直到 lock.notify()
或 lock.notifyAll()
唤醒它们。