多线程20:管程法

Posted duanfu

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了多线程20:管程法相关的知识,希望对你有一定的参考价值。

解决方式1:
 
并发协作模型"生产者/消费者模式"--->管程法
  • 生产者:负责生产数据的模块(可能是方法,对象,线程,进程)
  • 消费者:负责处理数据的模块(可能是方法,对象,线程,进程)
  • 缓冲区:消费者不能直接使用生产者的数据,他们之间有个缓冲区,生产者将生产好的数据放入缓冲区,消费者从缓冲区拿出数据

技术图片

 

思路:
1.首先有一个生产者,消费者、生产者只顾生产,消费者只管消费、
2.利用了一个缓冲区,缓冲了一个10个大小的数组
3.有个方法叫放入产品,产品丢进来的时候,我们判断一下缓冲区有没有满,如果满了的话,生产者就要等待了,
如果没有满,就将产品放进去,放进去之后有产品了,赶紧通知消费者消费
4.消费者就判断下能不能消费呢,有没有东西,有东西的话,我就可以直接消费,消费完了,就赶紧通知生产者生产。
如果没有东西呢,消费者就等待。等待生产者去通知他,生产者通知了,他就可以解除等待了。
  1 package com.thread.gaoji;
  2 
  3 //测试: 生产者消费者模型-->利用缓冲区解决:管程法
  4 
  5 //生产者 , 消费者 , 产品 , 缓冲区
  6 public class TestPC {
  7 
  8     public static void main(String[] args) {
  9         SynContainer container = new SynContainer();
 10 
 11         new Productor(container).start();
 12         new Consumer(container).start();
 13     }
 14 }
 15 
 16 //生产者
 17 class Productor extends Thread {
 18     SynContainer container;
 19 
 20     public Productor(SynContainer container) {
 21         this.container = container;
 22     }
 23 
 24     //生产
 25     @Override
 26     public void run() {
 27         for (int i = 0; i < 100; i++) {
 28             container.push(new Chicken(i));
 29             System.out.println("生产了" + i + "只鸡");
 30         }
 31     }
 32 }
 33 
 34 //消费者
 35 class Consumer extends Thread {
 36     SynContainer container;
 37 
 38     public Consumer(SynContainer container) {
 39         this.container = container;
 40     }
 41 
 42     //消费
 43     @Override
 44     public void run() {
 45         for (int i = 0; i < 100; i++) {
 46             System.out.println("消费了-->" + container.pop().id + "只鸡");
 47         }
 48     }
 49 }
 50 
 51 //产品
 52 class Chicken {
 53     int id;//编号
 54 
 55     public Chicken(int id) {
 56         this.id = id;
 57     }
 58 }
 59 
 60 //缓冲区
 61 class SynContainer {
 62 
 63     //需要一个容器大小
 64     Chicken[] chickens = new Chicken[10];
 65 
 66     //容器计数器
 67     int count = 0;
 68 
 69     //生产者放入产品
 70     public synchronized void push(Chicken chicken) {
 71         //如果容器满了,就需要等待消费者消费
 72         if (count == chickens.length) {
 73             //生产者等待
 74             try {
 75                 this.wait();
 76             } catch (InterruptedException e) {
 77                 e.printStackTrace();
 78             }
 79         }
 80         //如果没有满,我们需要丢入产品
 81         chickens[count] = chicken;
 82         count++;
 83 
 84         //可以通知消费者消费了.
 85         this.notifyAll();
 86     }
 87 
 88     //消费者消费产品
 89     public synchronized Chicken pop() {
 90         //判断能否消费
 91         if (count == 0) {
 92             //消费者等待
 93             try {
 94                 this.wait();
 95             } catch (InterruptedException e) {
 96                 e.printStackTrace();
 97             }
 98         }
 99 
100         //如果可以消费
101         count--;
102         Chicken chicken = chickens[count];
103 
104         //吃完了,通知生产者生产
105         this.notifyAll();
106         return chicken;
107     }
108 }

 

 

以上是关于多线程20:管程法的主要内容,如果未能解决你的问题,请参考以下文章

多线程——生产者消费者问题-----管程法

线程协作---生产者消费者模式之“管程法”实现

线程间的通信 与 线程池

《狂神说——多线程》

多线程_并发协作

多线程 Thread 线程同步 synchronized