java多线程生产者/消费者示例代码

多线程管理

  • 线程类
    –通过继承Thread或实现Runable
    – 通过start方法,调用run方法,run方法工作
    – 线程run结束后,线程退出
  • 粗粒度: 子线程与子线程之间、和main线程之间缺乏同步
  • 细粒度:线程之间有同步协作
    – 等待
    – 通知/唤醒
    – 终止
    • 等待:等A线程执行到某一个地方的时候,B线程告A线程,让A等待一会,等A到了,在往下一起走
    • 通知/唤醒: A到了,A告诉B,我到了,可以走了
    • 线程状态
      – NEW 刚创建(new)
      – RUNNABLE 就绪态(start)
      – RUNNING 运行中(run)
      – BLOCK 阻塞(sleep)
      – TERMINATED 结束
      在这里插入图片描述
  • Thread的部分API已经废弃
    – 暂停和恢复spspend/resume (这些方法很危险,已经废弃,不建议使用)
    – 消亡 stop/destroy (这些方法很危险,已经废弃,不建议使用)
  • 线程阻塞/和唤醒
    – sleep,时间一到,自己会醒来
    – wait/notify/notifyAll 等待,需要别人来唤醒
    – join 等待另外一个线程结束
    – interrupt 向另外一个线程发送中断信号,该线程收到信号,会触发InterruptedException(可解除阻塞),并进行下一步处理
    • wait: 休眠状态,等别的线程调用notify或者notifyAll的时候,可以醒来。一个等待(wait)的线程是需要其他线程去唤醒的,如果没有其他线程去唤醒它,那这个线程就一直等待,一直处于休眠状态

生产者/消费者示例:

经典生成者与消费者问题
生产者不断的往仓库中存放产品,消费者从仓库中消费产品。
其中生产者和消费者都可以有若干个。
仓库规则:容量有限,库满时不能存放,库空时不能取产品。

源码示例:

//产品
public class Product  {
    private Integer id;
    private String name;
    }
package product;

/**
 * @ClassName:Storage
 * @Description:仓库类
 * @author: Torey
 */
public class Storage {
    //仓库容量
    public Storage(Integer volume) {
        this.products = new Product[volume];
        this.volume=volume;
    }
    //仓库容量
    private Integer volume;

    public Integer getVolume() {
        return volume;
    }

    public void setVolume(Integer volume) {
        this.volume = volume;
    }

    //仓库容量
    private Product[] products ;

    private int top = 0;
//生产者向仓库中放入产品
    public synchronized void push(Product product){
        while (top == products.length) {
            try {
                System.out.println("product wait");
                wait();//仓库已满,等待
            }catch (Exception ex){
                ex.printStackTrace();
            }
        }
        //把产品放入仓库
        products[top++]=product;
        System.out.println("producer notifyAll"+Thread.currentThread().getName() + "生产了产品:"+product);
        notifyAll();//唤醒等待线程
    }
    //消费者从仓库中取出产品
    public synchronized Product pop() {
        while (top == 0) {
            try{
            System.out.println("empty! consumer wait");
            wait();}catch (Exception ex){
                ex.printStackTrace();
            }
        }
        //从仓库中取产品
        --top;
        Product p = new Product(products[top].getId(), products[top].getName());
        products[top]=null;
        System.out.println("comsumer notifyAll "+Thread.currentThread().getName() + " 消费了产品:" + p);
        notifyAll(); //唤醒等待的线程
        return p;
    }
}

package product;
/**
 * @ClassName:Consumer
 * @Description:消费者
 * @author: Torey
 */
public class Consumer implements Runnable {
    private Storage storage;

    /**
     *
     * @param storage 仓库
     * @param interval 多久消费一个
     */
    public Consumer(Storage storage,Integer interval) {
        this.storage = storage;
        this.integer=interval*1000;
    }
private Integer integer;
    @Override
    public void run() {
        int i=0;
        while (true){
            try {
                i++;
               storage.pop();
                Thread.sleep(integer);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
}
package product;
import java.util.Random;

/**
 * @ClassName:Producer
 * @Description:生产者
 * @author: Torey
 */
public class Producer implements Runnable {
    private Storage storage;

    /**
     *
     * @param storage 仓库
     * @param integer 多久生产一个
     */
    public Producer(Storage storage,Integer integer) {
        this.storage = storage;
        this.integer=integer*1000;
    }
    private Integer integer;
    @Override
    public void run() {
        int i=0;
        Random r = new Random();
        while (true){
            i++;
            Product product = new Product(i, "电话" + r.nextInt(100));
            try {
                Thread.sleep(integer);
                storage.push(product);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
}
package product;
/**
 * @ClassName:ProductTest
 * @Description:
 * 经典生成者与消费者问题
 * 生产者不断的往仓库中存放产品,消费者从仓库中消费产品。
 * 其中生产者和消费者都可以有若干个。
 * 仓库规则:容量有限,库满时不能存放,库空时不能取产品。
 * @author: Torey
 */
public class ProductTest {
    public static void main(String[] args) throws InterruptedException {
        //仓库容量为 5个
        Storage storage = new Storage(5);
        //每5秒钟消费一次
      new Thread(new Consumer(storage,5),"消费者1").start();
  //每秒生产一个
       new Thread(new Producer(storage,1),"生产者2").start();
    }
}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值