Java多线程 Producer and Consumer设计模式
作者:冬日毛毛雨 发布时间:2022-08-30 07:13:24
producer
是生产者的意思:指生产数据的线程,consumer
是消费者的意思:指的是使用数据的线程
public class ProducerThread extends Thread {
private final static Random random = new Random(System.currentTimeMillis());
private final static AtomicInteger counter = new AtomicInteger(0);
private final MessageQueue messageQueue;
public ProducerThread(MessageQueue messageQueue, int seq) {
super("Producer-" + seq);
this.messageQueue = messageQueue;
}
@Override
public void run() {
while (true) {
try {
Message message = new Message("Message-" + counter.getAndIncrement());
messageQueue.put(message);
System.out.println(Thread.currentThread().getName() + " put message " + message.getData());
Thread.sleep(random.nextInt(1000));
} catch (InterruptedException e) {
break;
}
}
}
}
public class ConsumerThread extends Thread {
private final static Random random = new Random(System.currentTimeMillis());
private final MessageQueue messageQueue;
public ConsumerThread(MessageQueue messageQueue, int seq) {
super("Consumer-" + seq);
this.messageQueue = messageQueue;
}
@Override
public void run() {
while (true) {
try {
Message message = messageQueue.take();
System.out.println(Thread.currentThread().getName() + " take a message " + message.getData());
Thread.sleep(random.nextInt(1000));
} catch (InterruptedException e) {
break;
}
}
}
}
public class Message {
public Message(String data) {
this.data = data;
}
private String data;
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
}
public class MessageQueue {
private final static int DEFAULT_MAX_LIMIT = 100;
private final LinkedList<Message> queue;
private final int limit;
public MessageQueue() {
this(DEFAULT_MAX_LIMIT);
}
public MessageQueue(final int limit) {
this.limit = limit;
this.queue = new LinkedList<>();
}
public void put(final Message message) throws InterruptedException {
synchronized (queue) {
while (queue.size() > limit) {
queue.wait();
}
queue.addLast(message);
queue.notifyAll();
}
}
public Message take() throws InterruptedException {
synchronized (queue) {
while (queue.isEmpty()) {
queue.wait();
}
Message message = queue.removeFirst();
queue.notifyAll();
return message;
}
}
public int getMaxLimit() {
return this.limit;
}
public int getMessageSize() {
synchronized (queue) {
return queue.size();
}
}
}
public class ProducerAndConsumerClient {
public static void main(String[] args) {
final MessageQueue messageQueue = new MessageQueue();
new ProducerThread(messageQueue, 1).start();
new ProducerThread(messageQueue, 2).start();
new ProducerThread(messageQueue, 3).start();
new ConsumerThread(messageQueue, 1).start();
new ConsumerThread(messageQueue, 2).start();
}
}
Producer-1 put message Message-0
Producer-3 put message Message-2
Producer-2 put message Message-1
Consumer-1 take a message Message-0
Consumer-2 take a message Message-1
Producer-2 put message Message-3
Consumer-1 take a message Message-2
Producer-2 put message Message-4
Consumer-2 take a message Message-3
Producer-3 put message Message-5
Producer-3 put message Message-6
Producer-3 put message Message-7
Consumer-1 take a message Message-4
Producer-2 put message Message-8
Consumer-2 take a message Message-5
Producer-3 put message Message-9
Producer-1 put message Message-10
Producer-1 put message Message-11
Producer-2 put message Message-12
省略...
来源:https://juejin.cn/post/7023247132865855524


猜你喜欢
- 前言一个说难不难,说简单竟看不出来是哪里问题的一个bug。是的 可能自己能力和经验尚浅无法识别,下面你们能否用火眼金睛一眼让bug原形毕露(
- 业务场景通常微服务对于用户认证信息解析有两种方案在 gateway 就解析用户的 token 然后路由的时候把 userId 等相关信息添加
- 本文实例为大家分享了Android仿Iphone屏幕底部弹出效果的具体代码,供大家参考,具体内容如下main.xml如下: <?xml
- 定义装饰者模式:在不改变原有对象的基础之上,动态的将功能附加到对象上,提供了继承更有弹性的替代方案,也体现了开闭原则案例需求一个人去咖啡店点
- 本文实例为大家分享了Android下载进度监听和通知的具体代码,供大家参考,具体内容如下下载管理器关于下载进度的监听,这个比较简单,以apk
- JavaWeb 使用DBUtils实现增删改查1、创建C3p0Utils类创建cn.itcast.jdbc.utils包代码如下:packa
- JUC包(java.util.concurrent)中提供了对定时任务的支持,即ScheduledExecutorService接口。本文对
- 一、目的本篇文章的目的是记录本人使用flutter加载与调用第三方aar包。二、背景本人go后端,业余时间喜欢玩玩flutter。一直有一个
- springboot 排除redis的自动配置因为要配置一个redis链接,所以将系统自带的配置排除,分别是RedisAutoConfigu
- 最近经朋友介绍开始玩 密传 网络游戏 升级升级,突然觉得太费键盘,于是自己用C#写了一个程序,想代替我的操作,自己去打怪物,自己升级 用这个
- 本文实例讲述了Android实现ListView异步加载的方法。分享给大家供大家参考,具体如下:@Override publi
- 一、Spring Boot Admin 的概念 Spring Boot Admin是一个
- try就像一个网,把try{}里面的代码所抛出的异常都网住,然后把异常交给catch{}里面的代码去处理。最后执行finally之中的代码。
- Spring Boot读取yml文件的主要方式有以下几种:1.@Value注解? 我们可以在bean的属性上使用@Value注解,直接读取y
- 我就废话不多说了,大家还是直接看代码吧~private LineRenderer line1; &
- 一、maven引入依赖,数据库驱动根据项目需求自行引入<!-- https://mvnrepository.com/artifact/
- NO.1–注释在程序中,尤其是复杂的程序中,适当地加入注释可以增加程序的可读性,有利于程序的修改、调试和交流。注释的内容
- 本文实例讲述了用WebBrowser操作frame和iframe的方法,比较适合C#初学者参考学习。示例浅显易懂,具体方法如下:
- java.lang.NoSuchMethodException: com.sun.proxy.$Proxy58.list错误解决办法玩web
- * 可以说是Android开发中最常用的东西之一。我们通过 * 可以监听对象的各种变化事件,并进行一些需要的处理,相当有用,而且使用起来也