生产者/消费者模式

来源:互联网 发布:nginx log 切割 编辑:程序博客网 时间:2024/06/03 19:13

等待/通知模式最经典的案例即生产者/消费者模式。

1.一生产与一消费:操作值

2.多生产与多消费:操作值

多生产与多消费有可能会造成假死,假死即线程进入warning等待状态。若全部线程进入warning状态,则整个项目处于停止状态。假死出现的原因即有可能连续唤醒同类,即生产者唤醒生产者,消费者唤醒消费者。

解决假死的办法即把notify()改为notifyAll(),这样它的原理不光是通知同类线程也包括异类。

下面的几种模式的目的是:生产者想List对象中放入数据,消费者从List中取出数据,List最大容量为1。

3.一生产与一消费:操作栈

4.一生产与一消费

对于wait条件改变解决方案是if换做while,对于假死仍采用notify换做notifyAll

5.多生产与一消费

6.多生产与多消费

MyStack.java

public class MyStack {private List list=new ArrayList();synchronized public void push(){try{while(list.size()==1){    //System.out.println("push操作中的"+Thread.currentThread().getName()+"线程状态是wait状态的");this.wait();}list.add("anything="+Math.random());this.notifyAll();System.out.println("push="+list.size());}catch(InterruptedException e){e.printStackTrace();}}synchronized public String pop(){String returnString="";    try{    while(list.size()==0){    System.out.println("pop操作中的"+Thread.currentThread().getName()+"线程状态是wait状态的");    this.wait();    }    returnString=""+list.get(0);    list.remove(0);    this.notifyAll();    System.out.println("pop="+list.size());    }catch(InterruptedException e){    e.printStackTrace();    }    return returnString; }}
P.java
public class P {private MyStack mystack;public P(MyStack mystack) {super();this.mystack=mystack;}public void pushServer(){mystack.push();}}
C.java
public class C {private MyStack mystack;public C(MyStack mystack) {super();this.mystack=mystack;}public void popServer(){System.out.println("pop= "+mystack.pop());}}
P_Thread.java
public class P_Thread extends Thread{private P p;public P_Thread(P p) {super();this.p=p;}public void run(){while(true){p.pushServer();}}}
C_Thread.java
public class C_Thread extends Thread{private C c;public C_Thread(C c) {super();this.c=c;}public void run(){while(true){c.popServer();}}}
Run.java
public static void main(String[] args){MyStack mystack=new MyStack();P p1=new P(mystack);P p2=new P(mystack);P p3=new P(mystack);P p4=new P(mystack);P p5=new P(mystack);C c1=new C(mystack);C c2=new C(mystack);C c3=new C(mystack);C c4=new C(mystack);C c5=new C(mystack);P_Thread a1=new P_Thread(p1);P_Thread a2=new P_Thread(p2);P_Thread a3=new P_Thread(p3);P_Thread a4=new P_Thread(p4);P_Thread a5=new P_Thread(p5);a1.start();a2.start();a3.start();a4.start();a5.start();C_Thread b1=new C_Thread(c1);C_Thread b2=new C_Thread(c2);C_Thread b3=new C_Thread(c3);C_Thread b4=new C_Thread(c4);C_Thread b5=new C_Thread(c5);b1.start();b2.start();b3.start();b4.start();b5.start();}}