Java 学习笔记 使用synchronized实现生产者消费者模式
本文为作者原创,允许转载,不过请在文章开头明显处注明链接和出处!!! 谢谢配合~
作者:stars-one
链接:https://www.cnblogs.com/stars-one/p/10701292.html
本篇大约有2265个字,阅读预计需要2.83分钟
说明
- Object.wait()使当前的线程进入到等待状态(进入到等待队列)
- Object.notifyAll() 唤醒等待中的全部线程
- Object.notify() 随机唤醒一个线程
代码
consumer.java
public class Consumer extends Thread {
List<Object> container;
/*表示当前线程共生产了多少件物品*/
private int count;
public Consumer(String name, List<Object> container) {
super(name);
this.container = container;
}
@Override
public void run() {
while(true){
synchronized (container) {
try {
if (container.isEmpty()) { //仓库已空,不能消 只能等
container.wait(20);
} else {
// 消费
container.remove(0);
this.count++;
System.out.println("消费者:" + getName() + " 共消费了:" + this.count + "件物品,当前仓库里还有" + container.size() + "件物品");
container.notifyAll(); // 唤醒等待队列中所有线程
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
try {
sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
Producer.java
public class Producer extends Thread{
List<Object> container;
/*表示当前线程共生产了多少件物品*/
private int count;
public Producer(String name, List<Object> container) {
super(name);
this.container = container;
}
@Override
public void run() {
while (true) {
synchronized (container) {
try {
// 如果某一个生产者能执行进来,说明此线程具有container对象的控制权,其它线程(生产者&消费者)都必须等待
if (container.size() == 10) { // 假设container最多只能放10个物品,即仓库已满
container.wait(10); //表示当前线程需要在container上进行等待
} else {
// 仓库没满,可以放物品
container.add(new Object());
this.count++;
System.out.println("生产者:" + getName() + " 共生产了:" + this.count + "件物品,当前仓库里还有" + container.size() + "件物品");
// 生产者生产了物品后应通知(唤醒)所有在container上进行等待的线程(生产者&消费者)
// 生:5, 消:5
// container.notify(); // 随机唤醒一个在等待队列中的线程
container.notifyAll(); // 唤醒等待队列中所有线程
}
} catch (InterruptedException e) {
e.printStackTrace();
}
} //
try {
sleep(20);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
Test.java
public class Test {
public static void main(String[] args) {
// 仓库
List<Object> container = new ArrayList<>();
new Producer("老王", container).start();
new Consumer("小芳", container).start();
new Producer("老李", container).start();
new Consumer("小荷", container).start();
new Producer("老张", container).start();
new Consumer("小花", container).start();
new Producer("老刘", container).start();
new Consumer("小妞", container).start();
new Consumer("小米", container).start();
new Producer("老马", container).start();
}
}
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】博客园携手 AI 驱动开发工具商 Chat2DB 推出联合终身会员
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 一个超经典 WinForm,WPF 卡死问题的终极反思
· ASP.NET Core - 日志记录系统(二)
· .NET 依赖注入中的 Captive Dependency
· .NET Core 对象分配(Alloc)底层原理浅谈
· 聊一聊 C#异步 任务延续的三种底层玩法
· 互联网不景气了那就玩玩嵌入式吧,用纯.NET开发并制作一个智能桌面机器人(一):从.NET IoT入
· .NET 开发的分流抢票软件,不做广告、不收集隐私
· 一个超经典 WinForm,WPF 卡死问题的终极反思
· 实现windows下简单的自动化窗口管理
· 前端实现 HTML 网页转 PDF 并导出