多线程模拟实现生产者/消费者模型 (借鉴)

简介: 在生产者/消费者模型中,生产者Producer负责生产数据,而消费者Consumer负责使用数据。多个生产者线程会在同一时间运行,生产数据,并放到内存中一个共享的区域。期间,多个消费者线程读取内存共享区,消费里面的数据。

 在生产者/消费者模型中,生产者Producer负责生产数据,而消费者Consumer负责使用数据。多个生产者线程会在同一时间运行,生产数据,并放到内存中一个共享的区域。期间,多个消费者线程读取内存共享区,消费里面的数据。

分析

在下面Java应用程序中,生产者线程向一个线程安全的堆栈缓冲区中写(PUSH)数据,消费者从该堆栈缓冲区中读(POP)数据,这样,这个程序中同时运行的两个线程共享同一个堆栈缓冲区资源。

类Producer是生产者模型,其中的run方法中定义了生产者线程所做的操作,循环调用push()方法,将生产的100个字母送入堆栈中,每次执行完push操作后,调用sleep方法睡眠一段随机时间。

类Consumer是消费者模型,循环调用pop方法,从堆栈取出一个字母,一共取100次,每次执行完push操作后,调用sleep方法睡眠一段随机时间

同步堆栈类SynchronizedStack

package com.ailk.biapp.ci.ProducerAndConsumer;

public class SynchronizedStack {
    private int index = 0;
    private int size = 100;
    //共享内存区
    private char[] data;
    
    public SynchronizedStack(int size){
        System.out.println("栈被创建");
        this.size = size;
        data = new char[size];
    }
    
     /**
     * 生产数据
     * 
     * @param c
     */
    public synchronized void push(char c){
        while (index == size){
            try{
                System.err.println("生产数据满了");
                this.wait();//等待,直到有数据出栈
            }catch(InterruptedException e){
                 Thread.currentThread().interrupt();
                 e.printStackTrace();
            }
        }
        data[index] = c;
        index++;
        this.notify();//通知其他线程把数据出栈 
    }
    
    /**
     * 消费数据
     * 
     * @return
     */
    public synchronized char pop(){
        while (index == 0){
            try{
                System.err.println("栈空了");
                this.wait();// 等待,直到有数据出栈
            }catch(InterruptedException e){
                Thread.currentThread().interrupt();
                e.printStackTrace();
            }
        }
        index --;//指针向下移动
        char ch = data[index];
        this.notify();//通知其他线程把数据入栈
        return ch;
    }
    
    //显示堆栈内容
    public synchronized void print(){
        for(int i = 0; i < data.length; i++){
            System.out.println(data[i]);
        }
        System.out.println();
        this.notify();// 通知其它线程显示堆栈内容
    }
    
}

生产者Product

package com.ailk.biapp.ci.ProducerAndConsumer;

public class Producer implements Runnable{
    private SynchronizedStack stack;
    
    public Producer(SynchronizedStack s){
        stack = s;
    }
    
    public void run(){
        char ch;
        for(int i = 0; i< 100; i++){
            //随机产生100个字符
            ch = (char) (Math.random() * 26 + 'A');
            stack.push(ch);
            System.out.println("Produced:" + ch);
            try{
                //每一个字符线程就休眠一下
                 Thread.sleep((int) (Math.random() * 1000));
            }catch (InterruptedException e) {
        }
    }
    }
}

消费者Consumer

package com.ailk.biapp.ci.ProducerAndConsumer;

public class Consumer implements Runnable{
    private SynchronizedStack stack;
    
    public Consumer(SynchronizedStack s){
        stack = s;
    }
    
    public void run() {
        char ch;
        for(int i = 0 ; i < 100; i++){
            ch = stack.pop();
            System.out.println("Consumed:" + ch);
        }
        try{
             Thread.sleep((int) (Math.random() * 1000));
        }catch(InterruptedException e){
            
        }
        
    }

}

测试:

package com.ailk.biapp.ci.ProducerAndConsumer;

public class ProductConsumerTest {
    public static void main(String args[]){
        // 下面的消费者类对象和生产者类对象所操作的是同一个同步堆栈对象
        SynchronizedStack stack = new SynchronizedStack(5);
        Runnable source = new Producer(stack);
        Runnable sink = new Consumer(stack);

        Thread t1 = new Thread(source);
        Thread t2 = new Thread(sink);
        t1.start();
        t2.start();
    }
}

借鉴于:http://www.cnblogs.com/linjiqin/archive/2011/04/15/2016820.html

目录
相关文章
|
2月前
|
Java
网络 I/O:单 Selector 多线程(单线程模型)
网络 I/O:单 Selector 多线程(单线程模型)
|
1月前
|
人工智能 JSON 前端开发
【Spring boot实战】Springboot+对话ai模型整体框架+高并发线程机制处理优化+提示词工程效果展示(按照框架自己修改可对接市面上百分之99的模型)
【Spring boot实战】Springboot+对话ai模型整体框架+高并发线程机制处理优化+提示词工程效果展示(按照框架自己修改可对接市面上百分之99的模型)
|
3月前
|
存储 NoSQL Redis
单线程模型想象不到的高并发能力、多路复用是效率杠杆
单线程模型想象不到的高并发能力、多路复用是效率杠杆
|
5月前
|
存储 NoSQL 调度
redis线程模型
redis线程模型
40 0
|
2月前
|
消息中间件 安全 Java
多线程(初阶七:阻塞队列和生产者消费者模型)
多线程(初阶七:阻塞队列和生产者消费者模型)
31 0
|
3月前
|
缓存 NoSQL 安全
Redis 新特性篇:多线程模型解读
Redis 新特性篇:多线程模型解读
49 5
|
3月前
|
存储 缓存 NoSQL
Redis 数据结构+线程模型+持久化+内存淘汰+分布式
Redis 数据结构+线程模型+持久化+内存淘汰+分布式
311 0
|
3月前
|
存储 缓存 NoSQL
《吊打面试官》系列-Redis双写一致性、并发竞争、线程模型
《吊打面试官》系列-Redis双写一致性、并发竞争、线程模型
39 0
|
3月前
|
网络协议 Linux API
基于Linux socket聊天室-多线程服务器模型(01)
基于Linux socket聊天室-多线程服务器模型(01)
46 0
|
3月前
|
网络协议 Linux API
从0实现基于Linux socket聊天室-多线程服务器模型(一)
从0实现基于Linux socket聊天室-多线程服务器模型(一)
41 0