在Java中实现生产者消费者模型时,如何正确使用synchronized和wait/notify机制来控制线程协作?请结合代码示例说明。
时间: 2024-12-07 08:21:01 浏览: 27
在Java并发编程中,生产者消费者模型是理解线程间协作的核心场景之一。使用`synchronized`关键字和`wait()`/`notify()`方法是实现线程安全通信的基本方式。首先,你需要同步块或方法,以确保在任何给定时间点只有一个线程可以访问共享资源。
参考资源链接:[Java并发编程:线程间通信与协作](https://wenku.csdn.net/doc/1gc523mjtp?spm=1055.2569.3001.10343)
具体来说,你需要两个主要的结构:一个共享资源缓冲区(例如队列)和两个锁对象,分别用于控制生产者和消费者的活动。通常,一个锁用于控制生产者,另一个用于控制消费者。在生产者代码中,当缓冲区已满时,生产者应调用`wait()`方法等待。类似地,消费者在缓冲区为空时调用`wait()`。当消费者从缓冲区取出一个项目时,它需要通知等待的生产者可以生产新项目,反之亦然。
以下是一个简单的代码示例,展示了如何使用`synchronized`和`wait()`/`notify()`来实现生产者和消费者之间的通信:
```java
class SharedQueue {
private Queue<String> buffer = new LinkedList<>();
private final int capacity = 10;
public void produce(String item) throws InterruptedException {
synchronized (buffer) {
while (buffer.size() == capacity) {
buffer.wait(); // 生产者等待,直到消费者消费
}
buffer.add(item);
buffer.notifyAll(); // 通知所有等待的线程
}
}
public String consume() throws InterruptedException {
synchronized (buffer) {
while (buffer.isEmpty()) {
buffer.wait(); // 消费者等待,直到生产者生产
}
String item = buffer.poll();
buffer.notifyAll(); // 通知所有等待的线程
return item;
}
}
}
```
在这个例子中,`produce`方法和`consume`方法都使用了同一个`buffer`对象作为锁。生产者在缓冲区满时调用`buffer.wait()`,而消费者在缓冲区空时调用`buffer.wait()`。在每种情况下,相应的`notifyAll()`调用将唤醒所有等待的线程。
了解这个基本模型后,你可以进一步探索`ReentrantLock`和`Condition`,它们提供了更灵活的线程协作机制。对于希望深入学习Java并发编程的读者,我建议阅读《Java并发编程:线程间通信与协作》一书,它详细解释了各种线程协作技术,并提供了丰富的示例和最佳实践。
参考资源链接:[Java并发编程:线程间通信与协作](https://wenku.csdn.net/doc/1gc523mjtp?spm=1055.2569.3001.10343)
阅读全文