设为首页 加入收藏

TOP

生产者消费者问题的Java实现(一)
2015-02-02 14:39:25 来源: 作者: 【 】 浏览:32
Tags:生产者 消费者 问题 Java 实现

生产者和消费者是多线程经典的问题,生产者和消费者问题的核心是同步的问题,同步问题的核心是要保证同一个资源被多个线程并发访问时的完整性,常用的方法是采用信号或加锁机制,保证资源在任一时刻只能被一个线程访问。这一问题用java来实现的话主要有4种方式。1.wait()/notify();2.await()/signal(); 3.blockingQuene 4.PipedInputStream/pipedOutputStream


下面分别来实现。


1.利用wait()和notify()来实现
Wait()方法:当缓冲区已空/满时,生产者/消费者停止自己的执行,放弃锁,使自己处于等待状态,让其他线程执行。


Notify()方法:当生产者/消费者向缓冲区放入/取出一个产品时,向其他等待的线程发出可执行的通知,同时放弃锁,使自己处于等待状态。


下面看看代码实现:


首先定义商店类:


package ConsumerAndProducerProblem;
?
import java.util.LinkedList;
?
/**
?* @author: zhuwei
?* @ClassName: 商店类
?* @Description: TODO
?* @Date: 下午3:58:01
?*/
public class Storage
{
?
? ? //定义仓库最大容量100
? ? private final int MAX_SIZE = 100;
? ? private LinkedList list= new LinkedList<>();
?
? ? //生产num个商品
? ? public void produce(int num) throws Exception
? ? {
? ? ? synchronized(list)
? ? ? {
? ? ? ? ? //假如仓库容量不足
? ? ? ? ? if(list.size()+num>MAX_SIZE)
? ? ? ? ? {
? ? ? ? ? ? ? System.out.println("仓储容量不足");
? ? ? ? ? ?
? ? ? ? ? ? ? //线程等待
? ? ? ? ? ? ? list.wait();
? ? ? ? ? }
? ? ? ? ? //仓库容量可以容量生产者的生产,则生产
? ? ? ? ? for(int i = 0;i < num;i++)
? ? ? ? ? {
? ? ? ? ? ? ? list.add(new Object());
? ? ? ? ? }
? ? ? ? ? System.out.println("生产者生产产品数量为:"+ num);
? ? ? ? ? list.notifyAll();
? ? ? }
? ? }
?
? ? //消费num个商品
? ? public void consume(int num) throws Exception
? ? {
? ? ? synchronized(list)
? ? ? {
? ? ? ? ? //加入仓库中的商品不能满足消费者的需求,线程等待
? ? ? ? ? if(list.size() < num)
? ? ? ? ? {
? ? ? ? ? ? ? System.out.println("仓库中的商品不能满足消费者需求");
? ? ? ? ? ? ? list.wait();
? ? ? ? ? }
? ? ? ? ? for(int i = 0;i < num;i++)
? ? ? ? ? {
? ? ? ? ? ? ? list.remove();
? ? ? ? ? }
? ? ? ? ? System.out.println("消费者消费商品数量为:"+num);
? ? ? ? ? list.notifyAll();
? ? ? }
? ? }
}


定义生产者类


package ConsumerAndProducerProblem;
?
?
/**
?* @author: zhuwei
?* @ClassName: 生产者线程
?* @Description: TODO
?* @Date: 下午3:57:15
?*/
public class Consumer implements Runnable
{
?
? ? //消费商品数量
? ? private int number;
?
? ? private Storage storage;
?
?
? ? public void consume(int num)
? ? {
? ? ? try
? ? ? {
? ? ? ? ? storage.consume(num);
? ? ? } catch (Exception e)
? ? ? {
? ? ? ? ? // TODO Auto-generatedcatch block
? ? ? ? ? e.printStackTrace();
? ? ? }
? ? }
?
? ? public int getNumber()
? ? {
? ? ? return number;
? ? }
?
?
?
? ? public void setNumber(int number)
? ? {
? ? ? this.number = number;
? ? }
?
?
?
? ? public Storage getStorage()
? ? {
? ? ? return storage;
? ? }
?
?
?
? ? public void setStorage(Storage storage)
? ? {
? ? ? this.storage = storage;
? ? }
?
?
?
? ? @Override
? ? public void run()
? ? {
? ? ? // TODO Auto-generatedmethod stub
? ? ? consume(number);
? ? }
?
}


定义消费者类:


package ConsumerAndProducerProblem;
?
/**
?* @author: zhuwei
?* @ClassName: 消费者线程
?* @Description: TODO
?* @Date: 下午3:57:38
?*/
public class Producer implements Runnable
{
? ? //生产的商品数量
? ? private int number;
?
? ? private Storage storage;
?
? ? public void produce(int num)
? ? {
? ? ? try
? ? ? {
? ? ? ? ? storage.produce(num);
? ? ? } catch (Exception e)
? ? ? {
? ? ? ? ? // TODO Auto-generatedcatch block
? ? ? ? ? e.printStackTrace();
? ? ? }
? ? }
?
? ? public int getNumber()
? ? {
? ? ? return number;
? ? }
?
? ? public void setNumber(int number)
? ? {
? ? ? this.number = number;
? ? }
?
? ? public Storage getStorage()
? ? {
? ? ? return storage;
? ? }
?
? ? public void setStorage(Storage storage)
? ? {
? ? ? this.storage = storage;
? ? }
?
? ? @Override
? ? public void run()
? ? {
? ? ? // TODO Auto-generatedmethod stub
? ? ? produce(number);
? ? }
?
}


创建测试类:


package ConsumerAndProducerProblem;
?
public class Test
{
?
? ? public static void main(String[] args)
? ? {
? ? ? // TODO Auto-generatedmethod stub
? ? ? //仓库对象
? ? ? Storage storage = new Storage();
? ? ?
? ? ? //消费者对象
? ? ? Consumer c1 = new Consumer();
? ? ? c1.setNumber(10);
? ? ? c1.setStorage(storage);
? ? ? Consumer c2 = new Consumer();
? ? ? c2.set

首页 上一页 1 2 下一页 尾页 1/2/2
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇Java集合中Comparable和Comparato.. 下一篇C# 之 扩展方法

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容: