多线程的典型应用场景---多个生产者多个消费者对共享资源的处理

 

 

1.生产者线程


/**
* 生产者线程
* (实际上是线程要执行的任务)
*/
public class ProduceRunnable implements Runnable {
private ProductFactory factory;
public ProduceRunnable(ProductFactory factory) {
this.factory = factory;
}
@Override
public void run() {
int i=1;
while(true){
factory.produce("商品"+i);
i++;
try {
Thread.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}

 

2.消费者线程

/**
* 消费者线程
*/
public class ConsumeRunnable implements Runnable{
private ProductFactory factory;
public ConsumeRunnable(ProductFactory factory) {
this.factory = factory;
}
@Override
public void run() {
while(true){
//消费一个商品
factory.consume();
//
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}


3.商品工厂


/**
* 商品工厂
*/
public class ProductFactory {
private List<String> list = new ArrayList<String>();
private int max = 10;
/**
* 生产商品
* @param productName
*/
public synchronized void produce(String productName){//
//如果仓库满,不再生产
while (list.size() ==max ){
try {
this.wait(); //是否锁,进入等待队列
} catch (InterruptedException e) {
e.printStackTrace();
}
}
//生产商品
list.add(productName);
System.out.println(Thread.currentThread().getName()+"生产商品:"+productName+",目前商品数量:"+list.size());
//通知消费者消费
this.notify();//生产者消费者使用同一把锁,所以wait()的生产者和消费者都在一个等待队列中。谁敢保证唤醒的不是生产者
}
/**
* 消费商品
*/
public synchronized void consume(){
//如果仓库为空,就等待
while(list.size()==0){
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
//消费商品
String productName = list.remove(0);
System.out.println(Thread.currentThread().getName()+"消费商品:"+productName+",目前商品数量:"+list.size());
//通知生产者
this.notify();
}
}


4.测试类


/**
* 功能:生产者消费者问题
* 多个生产者 多个消费者 多个商品
* 最多10个商品,最少0个商品
* 已经有10个商品,生产者不再生产,还要通知消费者消费
* 没有商品了,消费者不再消费,还要通知生产者生产
*/
public class Test {
public static void main(String[] args) {
//创建并启动多个生产者和消费者线程
ProductFactory factory = new ProductFactory();
Runnable target1 = new ProduceRunnable(factory);
for (int i = 0; i <5 ; i++) {
new Thread(target1,"生产者"+i).start();
}
Runnable target2 = new ConsumeRunnable(factory);
for (int i=0;i<10;i++){
new Thread(target2,"消费者"+i).start();
}
}
}

 

posted @ 2019-04-16 20:25  HandsomeEric  阅读(728)  评论(0编辑  收藏  举报