4

我读过很多关于线程状态的文档,其中一些说有两种不同的状态:阻塞(同步之前)和等待(如果调用等待),还有一些说只有一种状态:等待。此外,一些文档告诉你应该为每个 wait() 调用 notify() ,如果你不这样做,那么即使监视器被解锁,线程 waiting() 也永远不会有资格执行。

4

4 回答 4

13

从你最后一句话,我看到你并不完全理解synchronizedand wait()/之间的区别notify()

基本上,监视器有lockcondition。这几乎是正交的概念。

  • 当线程进入一个synchronized块时,它会获得一个锁。当线程离开该块时,它会释放锁。只有一个线程可以锁定特定的监视器。

  • 当有锁的线程调用wait()时,它会释放锁并开始等待它的条件。当有锁的线程调用notify()时,等待条件的线程之一(在 的情况下为所有线程notifyAll())有资格执行(并开始等待获取锁,因为通知线程仍然拥有它)。

因此,等待获取锁 (Thread.State.BLOCKED) 和等待监视器状态 (Thread.State.WAITING) 是不同且独立的状态。

如果你看一下类,这种行为会变得更加清晰Lock——它实现了与块相同的同步原语synchronized(带有一些扩展),但在锁和条件之间提供了明显的区别。

于 2010-10-06T13:15:56.090 回答
1

标准文档在这里

当一个线程调用Object.wait 方法时,它会释放这个获取的监视器并进入WAITING(或者 TIMED_WAITING如果我们调用等待方法的超时版本)状态。现在,当线程notify()通过调用或notifyAll()调用同一对象得到通知时,线程的等待状态结束,线程开始尝试重新获得它在等待调用时获得的所有监视器。有一次可能有几个线程试图重新获得(或者可能是第一次获得)他们的监视器。如果多个线程尝试获取特定对象的监视器,则只有一个线程(由JVM调度程序选择)被授予监视器,所有其他线程都进入BLOCKED状态。

于 2010-10-06T13:02:00.140 回答
1

两种不同的状态BLOCKED 和 WAITING。

如果没有人通知(或打断)您,则永远等待的部分是正确的。

于 2010-10-06T13:06:39.417 回答
0

在 Java 的观点(Thread.State)中,有两种不同的状态:BLOCKED 和 WAITING。当一个线程在一个对象上同步时,它处于 BLOCKED 状态。线程执行 wait 后,处于 WAITING 状态。

在 Linux 平台上,Java 线程是 OS 原生线程。BLOCKED 和 WAITING 状态的 OS 线程状态都是可中断睡眠。使用 ps 检查时,BLOCKED 和 WAITING 线程的状态都是“Sl+”。

于 2013-05-30T13:32:31.000 回答