Java-notifyAll()和notify()失败?可能吗?

Java-notifyAll()和notify()失败?可能吗?,java,Java,这对我来说真的很奇怪,但在我的程序中似乎notifyAll()/notify()失败了。 代码相当复杂,基本上我有三个线程A,B,C A向B发送请求,并在请求上等待()10秒超时,当B完成时,它调用notify()唤醒A 在一个死循环中,C通过一个队列将许多字符串提供给a,a提取它们并打印出来。每次A打印出一个字符串时,它都会向B发送一个请求并等待 因此,工作流程是: C一直在死循环中给a供电 A从C打印出字符串 A向B发送请求并等待(10) 通知 A从C打印出字符串 .... 一次又一次 这

这对我来说真的很奇怪,但在我的程序中似乎notifyAll()/notify()失败了。 代码相当复杂,基本上我有三个线程A,B,C

A向B发送请求,并在请求上等待()10秒超时,当B完成时,它调用notify()唤醒A

在一个死循环中,C通过一个队列将许多字符串提供给a,a提取它们并打印出来。每次A打印出一个字符串时,它都会向B发送一个请求并等待

因此,工作流程是:

C一直在死循环中给a供电

  • A从C打印出字符串
  • A向B发送请求并等待(10)
  • 通知

  • A从C打印出字符串 .... 一次又一次

  • 这在最初几秒钟内有效。但是,过了一段时间,我看到当B打印出它有notify()a时,a仍在等待,因为C用来向a提供信息的队列正在快速增加,a没有打印字符串。最后,10秒后,a抱怨请求超时

    这看起来像是notify()失败了,因为B在调用notify()后打印了消息。鉴于等待/通知是java的根本特性,我不敢相信它会失败。有可能吗?

    notify()只有在有线程等待时才起作用

    您应该使用的习惯用法是更改与notify()/notifyAll()相同的同步块中的状态。在等待块中,重复检查状态更改。这样,如果通知触发得太早,就会有状态更改来记录它。另外,如果wait错误唤醒,如果状态没有改变,它将再次等待

    public synchronized void notifyReady() {
        ready = true;
        notifyAll();
    }
    
    public synchronized void waitForReady() throws InterruptedException {
        while(!ready)
          wait();
    }
    

    你确定A“还在等”吗?另一种可能是,它在通知后开始等待,这将是一个被破坏的代码。(你不应该等待已经发生的事情。)也许B在A打电话之前已经打了通知wait@david“你不应该等待已经发生的事情”。我喜欢这个。也许B在A调用wait()之前完成了它的工作并调用了notify()?无论如何,使用类似于a的东西来同步a和B可能会更好。这比wait()/notify()更容易推理,因此可以避免像这样令人讨厌的计时错误。如果没有代码,很难判断您是否确定在等待和通知过程中锁定了同一个对象?谢谢大家。时间问题已被证明是原因