写一个生产者消费者的例子

package com.shopping.test;

public class ShaoKao {
    //
    String chuan;

    //
    String rou;

    //烧烤的状态,初始状态为没有烧烤
    boolean flag = false;

    public String getChuan() {
        return chuan;
    }

    public void setChuan(String chuan) {
        this.chuan = chuan;
    }

    public String getRou() {
        return rou;
    }

    public void setRou(String rou) {
        this.rou = rou;
    }

    public boolean isFlag() {
        return flag;
    }

    public void setFlag(boolean flag) {
        this.flag = flag;
    }
}

下面是生产者

package com.shopping.test;

/*
 * 注意:
 *     烧烤铺线程和吃货线程关系--->通信(互斥)
 *     必须使用同步技术保证两个线程只能有一个在执行
 *  锁对象必须保证唯一,可以使用烧烤对象作为锁对象
 *  烧烤铺类和吃货类就需要把烧烤对象作为参数传进去
 *  1. 需要在成员位置创建一个烧烤变量
 *  2. 使用带参数构造方法,为这个烧烤变量赋值
 */
public class ShaoKaoPu extends Thread {
    //1. 需要在成员位置创建一个烧烤变量,作为锁对象
    private ShaoKao bz;

    //2. 使用带参数构造方法,为这个烧烤变量赋值
    public ShaoKaoPu(ShaoKao bz) {
        this.bz = bz;
    }

    //设置线程任务(run), 生产烧烤
    public void run() {
        //定义一个变量,这个变量决定到底要做什么馅的烧烤
        int count = 0;
        //死循环,让烧烤铺一直生产烧烤
        while(true) {
            //必须使用同步技术保证两个线程只能有一个在执行
            synchronized(bz) {
                //对烧烤的状态进行判断
                if(bz.flag == true) {
                    //已经有烧烤了,不用生产,烧烤铺调用wait方法进入等待状态
                    try {
                        bz.wait();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
                //被吃货唤醒之后,证明没有烧烤了,又要开始生产烧烤
                //增加一些趣味性:交替生产烧烤
                if(count % 2 == 0) {
                    //生产 羊肉烤串
                    bz.chuan = "大串";
                    bz.rou = "羊肉";
                }else {
                    //生产 牛肉大葱馅
                    bz.chuan = "大串";
                    bz.rou = "羊肉";
                }
                count++;
                System.out.println("烧烤铺正在生产:" + bz.chuan + bz.rou + "烧烤");
                //生产烧烤需要3秒钟
                try {
                    Thread.sleep(3000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                //烧烤铺生产好了烧烤,修改烧烤的状态为true有
                bz.flag = true;
                //唤醒吃货线程起来吃烧烤
                bz.notify();
                //烧烤铺已经生产好了烧烤
                System.out.println("烧烤铺已经生产好了" + bz.chuan + bz.rou + "烧烤" + "吃货可以开始吃了");
            }
        }

    }
}

消费者

package com.shopping.test;

public class ChiHuo extends Thread{

    //1. 需要在成员位置创建一个烧烤变量,作为锁对象
    private ShaoKao bz;

    //2. 使用带参数构造方法,为这个烧烤变量赋值
    public ChiHuo(ShaoKao bz) {
        this.bz = bz;
    }
    //设置线程任务(run), 吃烧烤
    public void run() {
        //死循环,让吃货一直吃烧烤
        while(true) {
            //必须使用同步技术保证两个线程只能有一个在执行
            synchronized(bz) {
                //对烧烤的状态进行判断
                if(bz.flag == false) {
                    //发现没有烧烤,吃货调用wait方法进入等待状态,等烧烤铺做好烧烤
                    try {
                        bz.wait();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
                //被烧烤铺唤醒之后,证明有烧烤吃了
                System.out.println("吃货正在吃:" + bz.chuan + bz.rou + "的烧烤");
                //吃货吃完烧烤
                //修改烧烤的状态为false没有
                bz.flag = false;
                //吃货唤醒烧烤铺线程,继续生产烧烤
                bz.notify();
                System.out.println("吃货已经把:" + bz.chuan + bz.rou + "的烧烤吃完了");
                System.out.println("---------------------------------------------------------------------------");
            }
        }
    }
}

 

测试:

package com.shopping.test;

public class Test {

    public static void main(String[] args) {
        //创建烧烤对象,作为锁对象
        ShaoKao bz = new ShaoKao();
        //创建烧烤铺线程
        new ShaoKaoPu(bz).start();
        //开启吃货线程
        new ChiHuo(bz).start();
    }
}

 

输出的是: 

    

烧烤铺正在生产:大串羊肉烧烤
烧烤铺已经生产好了大串羊肉烧烤吃货可以开始吃了
吃货正在吃:大串羊肉的烧烤
吃货已经把:大串羊肉的烧烤吃完了
---------------------------------------------------------------------------
烧烤铺正在生产:大串羊肉烧烤
烧烤铺已经生产好了大串羊肉烧烤吃货可以开始吃了
吃货正在吃:大串羊肉的烧烤
吃货已经把:大串羊肉的烧烤吃完了
---------------------------------------------------------------------------
烧烤铺正在生产:大串羊肉烧烤
烧烤铺已经生产好了大串羊肉烧烤吃货可以开始吃了
吃货正在吃:大串羊肉的烧烤
吃货已经把:大串羊肉的烧烤吃完了
---------------------------------------------------------------------------

 

  

posted @ 2019-08-25 11:33  坠落凡尘的魔鬼  阅读(1261)  评论(0编辑  收藏  举报