笔试题11:编写一个生产者与消费者的多线程例子(源码)

 生产者与消费者模式,是一道非常经典的设计模式,所涉及到的是多线程协调工作的问题。在Java中,一般是通过wait()和notify()方法进行解决。

下面附上关于这种设计模式的源码:

[java]  view plain copy
  1. //仓库类  
  2. public class Store {  
  3.       
  4.     private final int MAX_SIZE;//仓库的最大容量  
  5.     private int count;//当前的货物数量  
  6.     public Store(int n){//初始化最大容量的构造方法  
  7.         MAX_SIZE = n;  
  8.         count = 0;  
  9.     }  
  10.       
  11.     //往仓库加货物的方法  
  12.       
  13.     public synchronized void add(){  
  14.         while(count >= MAX_SIZE){//每次执行都判断仓库是否已满  
  15.             System.out.println("已经满了");  
  16.             try {  
  17.                 this.wait();//如果满了,就进入等待池  
  18.             } catch (Exception e) {  
  19.                 e.printStackTrace();  
  20.             }  
  21.         }  
  22.         count++;//数量加1  
  23.         //打印当前仓库的货物数量  
  24.         System.out.println(Thread.currentThread().toString()+"put"+count);  
  25.         //仓库中已经有东西可以取了,则通知所有的消费者线程来拿  
  26.         this.notifyAll();  
  27.     }  
  28.       
  29.     //从仓库拿走货物的方法  
  30.     public synchronized void remove(){  
  31.         while(count<=0){  
  32.             System.out.println("空了");//每次执行都判断仓库是否为空  
  33.             try {  
  34.                 this.wait();//如果为空,就进入等待池  
  35.             } catch (Exception e) {  
  36.                 e.printStackTrace();  
  37.             }  
  38.         }  
  39.         //打印当前仓库的货物数量  
  40.         System.out.println(Thread.currentThread().toString()+"get"+count);  
  41.         count--;//数量减1  
  42.         //仓库还没装满,通知生产者添加货物  
  43.         this.notifyAll();  
  44.     }  
  45.   
  46.     /** 
  47.      * @param args 
  48.      */  
  49.     public static void main(String[] args) {  
  50.         Store s = new Store(5);  
  51.         //创建两个生产者和两个消费者  
  52.         Thread pro1 = new Producer(s);  
  53.         Thread con1 = new Consumer(s);  
  54.         Thread pro2 = new Producer(s);  
  55.         Thread con2 = new Consumer(s);  
  56.         pro1.setName("producer1");  
  57.         con1.setName("consumer1");  
  58.         pro2.setName("producer2");  
  59.         con2.setName("consumer2");  
  60.         //启动线程  
  61.         pro1.start();  
  62.         con1.start();  
  63.         pro2.start();  
  64.         con2.start();  
  65.           
  66.   
  67.     }  
  68.   
  69. }  
  70.   
  71. class Producer extends Thread{//生产者线程类  
  72.     private Store s;  
  73.     public Producer(Store s){  
  74.         this.s = s;  
  75.     }  
  76.     public void run(){//线程方法  
  77.         while(true){//循环  
  78.             s.add();//往仓库加货物  
  79.             try {  
  80.                 Thread.sleep(1000);//设置线程休息1s  
  81.             } catch (Exception e) {  
  82.                 e.printStackTrace();  
  83.             }  
  84.         }  
  85.     }  
  86. }  
  87. class Consumer extends Thread{//消费者线程类  
  88.     private Store s;  
  89.     public Consumer(Store s){  
  90.         this.s = s;  
  91.     }  
  92.     public void run(){//线程方法  
  93.         while(true){//循环  
  94.             s.remove();//从仓库取走货物  
  95.             try {  
  96.                 Thread.sleep(1500);//设置线程休息1.5s  
  97.             } catch (Exception e) {  
  98.                 e.printStackTrace();  
  99.             }  
  100.         }  
  101.     }  
  102. }  

运行结果如下:

[plain]  view plain copy
  1. ……  
  2. Thread[producer1,5,main]put5  
  3. Thread[consumer2,5,main]get5  
  4. Thread[consumer1,5,main]get4  
  5. Thread[producer2,5,main]put4  
  6. Thread[producer1,5,main]put5  
  7. 已经满了  
  8. Thread[consumer2,5,main]get5  
  9. Thread[producer2,5,main]put5  
  10. Thread[consumer1,5,main]get5  
  11. Thread[producer1,5,main]put5  
  12. 已经满了  
  13. Thread[consumer1,5,main]get5  
  14. ……  

其中,我们可以通过调节两个线程类的
[java]  view plain copy
  1. Thread.sleep(1000);  

来控制生产者与消费者的关系。


  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值