notify() 不保证唤醒指定线程,仅随机唤醒等待队列中一个线程,被唤醒者需重新竞争锁;无法指定目标是因监视器机制不记录线程身份且无相关API;精准唤醒应改用Condition、标志位+notifyAll或阻塞队列等替代方案。
Java 中 Object 类的 notify() 方法**并不保证唤醒“单个指定”线程**,它只是从当前对象监视器(monitor)的等待队列中**随机唤醒一个正在 wait() 的线程**——这个“单个”是存在性意义上的(唤醒一个,而非全部),但不是可控、可选择的“某一个”。
notify() 的设计目标是打破等待状态,避免虚假唤醒或资源竞争,但它不提供线程选择能力:
WAITING 状态的线程,具体选哪个由 JVM 决定,不可预测;notify() 不做任何事,无异常也无提示。这是 Java 内存模型和监视器机制的设计限制:
wait()/notify() 基于对象级别的监视器,不记录线程身份或优先级;若业务需要“唤醒某个特定等待者”,应放弃 notify(),改用更可控的协作机制:
立即学习“Java免费学习笔记(深入)”;
java.util.concurrent 工具类:如 Condition 配合 ReentrantLock,可为不同等待条件创建多个 Condition 实例,实现分组唤醒;wait();LinkedBlockingQueue)或信号量(Semaphore):将“唤醒请求”建模为数据或许可,让目标线程主动消费。以下写法看似“唤醒单个”,实则不可靠:
❌ 错误示例:synchronized (obj) { obj.notify(); // 无法确保唤醒的是你期望的那个线程}
即使只有一条线程在等,也不建议依赖此行为做逻辑分支——因为多线程环境下,可能有新线程在 notify() 后、被唤醒前进入 wait(),导致唤醒错乱。