Oracle的jvm中的notify()实现

时间:2013-12-04 13:01:35

标签: java multithreading jvm implementation notify

我的印象是大多数人只使用Oracle提供的jvm实现(最初来自Sun microsystems)。如果我错了,请纠正我。

当我浏览API for notify()时,它说:

  

唤醒正在此对象监视器上等待的单个线程。如果   任何线程都在等待这个对象,其中一个被选中   惊醒。 选择是任意的,由酌情决定   实施。

我想知道以什么顺序在Oracle的jvm中调用notify()时将调用等待的线程。

你可能想知道我为什么不考虑使用notifyAll()而只是不用担心。但是,当我只使用notify()调用一个线程时,为什么要不必要地调用所有等待的线程?即使我使用notifyAll(),我也无法控制哪个等待线程将获得监视器。

Oracle应该在上面给出的api链接中记录它是如何在自己的实现中实现的。

3 个答案:

答案 0 :(得分:4)

使用Threads执行的顺序未定义。

如果您根据可以预测执行顺序的假设编写任何代码,它最多只能在一台机器上运行。因此,Oracle实际实现它的方式 - 除了研究案例 - 无关紧要,因为它可能在下一台机器甚至下一版本的Oracle JVM上实现不同。

如果您需要更精细的控制,那么您需要调整架构并以正确的方式使用concurrent package中的类。同步/等待/通知只是一个非常基本的“暴力”实现线程同步,具有许多陷阱和限制。

答案 1 :(得分:2)

您只能依赖API所说的内容,并且API不保证任何特定订单。如果您需要线程以某种顺序唤醒,请在公平模式下使用ReentrantLock,然后此锁定的Condition.signal()将唤醒等待此条件最长的线程。

答案 2 :(得分:0)

您可以在构造函数中使用带有公平标记的ReentrantLock(boolean fair)。从这种锁中创造的条件也是公平的:

  

使用给定的公平政策创建ReentrantLock实例。

  

从等待返回的线程的锁重新获取的顺序   方法与最初获取锁的线程相同,即   在默认情况下没有指定,但公平锁有利于那些   等待时间最长的线程。