问题描述
假如汽车公司只有一个生产车间, 一间存储仓库(仓库可存储做多n辆车),该公司只生产一种车型。现在需要模仿生产、销售过程。每生产一辆汽车,需要送入仓库临时存储,当仓库满后,停止生产,车辆的销售有一个前提条件是,库存大于零。问题分析
使用面向对象的思维,我们需要考虑类的设计生产车间(生产者):生产者生产汽车放入仓库,这个类包括生产汽车和调入指定库存两个方法
消费者:汽车取出仓库,这个类具有取出汽车的方法
仓库:库存数量,这个类需要统计汽车数量,当库存已满或者库存为空是发出消息
数据结构设计
仓库被设计成栈结构
考虑到汽车生产和销售是两个独立的过程,有必要使用多线程
代码描述
- public class ProducersConsumers {
- public static void main(String[] args) {
- Storage storage = new Storage();
- Producer producer = new Producer(storage);
- Consumer consumer = new Consumer(storage);
- new Thread(producer).start();
- new Thread(consumer).start();
- }
- }
- class Car{
- int id; //每辆汽车取一个id
- public Car(int id) {
- this.id = id;
- }
- }
- class Storage{
- int index; //用数组实现栈结构
- private static final int MAX_NUM = 20;
- Car[] carStack = new Car[MAX_NUM];
- //入库
- public synchronized void push(Car car){
- while (index == MAX_NUM){
- try {
- this.wait(); //仓库满时,入库线程等待
- }catch (InterruptedException e){}
- }
- this.notify(); //有可能空唤醒
- carStack[index] = car;
- index++;
- }
- //出库
- public synchronized Car pop( ){
- while (index == 0){
- try {
- this.wait(); //库存为空时,出库线程等待
- }catch (InterruptedException e){}
- }
- this.notify();
- index--;
- return carStack[index];
- }
- }
- class Producer implements Runnable{
- Storage storage = null;
- //每一辆汽车都会放入仓库,本例只有一个仓库
- public Producer(Storage storage) {
- this.storage = storage;
- }
- public void run( ) {
- for (int i = 0; i < 20; i++) {
- Car car = new Car(i);
- storage.push(car);
- System.out.println("生产了"+i+"辆汽车");
- try {
- Thread.sleep(100);
- }catch (InterruptedException e){}
- }
- }
- }
- class Consumer implements Runnable{
- Storage storage = null;
- //从仓库取出一辆汽车
- public Consumer(Storage storage) {this.storage = storage;}
- public void run( ) {
- for (int i = 0; i < 20; i++) {
- storage.pop();
- System.out.println("卖出了"+i+"辆汽车");
- try {
- Thread.sleep(100);
- }catch (InterruptedException e){}
- }
- }
- }
另外,在实际编码中,恰当使用锁的粒度、使用线程池、使用缓冲队列等都是可以提高的地方。