java生产者,消费者

有很多实现的方法

使用blockingqueue实现

demo

import java.util.concurrent.LinkedBlockingQueue;

/**
 * Created by 58 on 2017/11/27.
 */
public class proandconsu {
    private static LinkedBlockingQueue<Integer> buffer = new LinkedBlockingQueue<Integer>(5);

    public static void main(String[] args) {
        Thread c = new Thread(new Consumer());
        Thread p = new Thread(new Produceer());
        c.start();
        p.start();
        Thread m = new Thread(new MonitorBuffer());
        m.start();
    }


    //消费者
    static class Consumer implements  Runnable{

        //每隔两秒消费一个产品
        public void run() {
            while(true){
                try {
                    int product = buffer.take();
                    System.out.println("consume a product: " + product);
                    Thread.sleep(2000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    //生产者
    static class Produceer implements Runnable{
        //每隔一秒钟生成一个产品
        public void run() {
            int product = 0;
            while (true){
                System.out.println("produce one product.");
                try {
                    buffer.put(product);
                    Thread.sleep(500);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    //定时监控buffer数量
    static class MonitorBuffer implements Runnable{

        public void run() {
            while(true){
                System.out.println("buffer size : " + buffer.size());
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }
}

注意:

  1. 对buffer操作需要同步
  2. buffer没有内容需要阻塞消费者,buffer满了需要阻塞生产者
  3. linkedblockingqueue通过reentralock、wait、notify实现了上面两个要求

自定义容器实现生产者消费者

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * Created by 58 on 2017/11/27.
 * 使用自定义的buffer
 * 1. 同步生产者消费者对buffer的操作
 * 2. buffer满了,要阻塞生产者,buffer空了,要阻塞消费者
 */
public class ProandConsuUsingSelfDefineBuffer {
    private static Buffer<Integer> buffer = new Buffer<Integer>(5);

    public static void main(String[] args) {
        Thread c = new Thread(new Consumer());
        Thread p = new Thread(new Producer());
        c.start();
        p.start();
        Thread m = new Thread(new MonitorBuffer());
        m.start();
    }


    //消费者
    static class Consumer implements  Runnable{

        public void run() {
            while(true){
                try {
                    int product = buffer.take();
                    Thread.sleep(2000);
                    System.out.println("consumer consume product: " + product);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    //生产者
    static class Producer implements Runnable{

        public void run() {
            int product = 1;
            while(true){
                try {
                    buffer.put(product);
                    Thread.sleep(1000);
                    System.out.println("producer create product.");
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    //监控buffer大小
    static class MonitorBuffer implements Runnable{

        public void run() {
            while(true){
                System.out.println("buffer size: " + buffer.size());
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }


}

/**
 * 缓冲池
 * */
class  Buffer<T>{
    private List<T> container = new ArrayList<T>();
    private int size;
    private int defaultSize = 10;
    private static Lock lock = new ReentrantLock();
    private static Condition notFull = lock.newCondition();
    private static Condition notEmpty = lock.newCondition();

    public Buffer() {
        this.size = defaultSize;
    }

    public Buffer(int size) {
        this.size = size;
    }

    //生产者往里面放内容
    public void put(T product) throws InterruptedException {
        lock.lock();
        while(container.size() >= size){
            notFull.await();
        }
        container.add(product);
        if(container.size() > 0){
            notEmpty.signal();
        }
        lock.unlock();
    }

    //消费者消费内容
    public T take() throws InterruptedException {
        lock.lock();
        while(container.size() <= 0){
            notEmpty.await();
        }
        T product = container.remove(container.size() - 1);
        if(container.size() < size){
            notFull.signal();
        }
        lock.unlock();
        return product;
    }

    public int size(){
        return container.size();
    }
}

备注:

  1. 使用lock同步线程
  2. 使用lock condition阻塞、唤醒线程

posted on 2017-11-27 10:26  luckygxf  阅读(323)  评论(0)    收藏  举报

导航