生产者-消费者问题
生产者-消费者问题描述的是:有一群生产者进程在生产产品,并将这些产品提供给消费者进程去消费。为使生产者进程与消费者进程能够并发执行,在两者之间设置了一个具有n个缓冲区的缓冲池,生产者进程将它所生产的产品放入一个缓冲区中;消费者进程可以从一个缓冲区中取走产品去消费。尽管所有的生产者和消费者进程都是以异步方式运行的,但它们之间必须保持同步,即不允许消费者进程到一个空缓冲区去取产品;也不允许生产者进程向一个已经装满产品的缓冲区中投放产品
程序流程图
源代码
package 信号量操作;
import java.util.ArrayList;
import java.util.List;
public class Producer implements Runnable{
//创建一个集合,用来表示任务队列
private List<Integer> taskQueue = new ArrayList<Integer>();
//生产的量
private final int MAX_CAPACITY;
//初始化生产者
public Producer(List<Integer> sharedQueue,int size){
this.taskQueue = sharedQueue;
this.MAX_CAPACITY = size;
}
public void run()
{
//设初始为1
int counter = 1;
while (true)
{
try
{
//互斥信号量
synchronized (taskQueue)
{
//队列中的内容等于最大量的时候,表示已经满了
while (taskQueue.size() == MAX_CAPACITY)
{
System.out.println("队列已满 ," + Thread.currentThread().getName() +
"处于等待 , 大小: " + taskQueue.size());
taskQueue.wait();
}
//休眠1秒
Thread.sleep(1000);
//加入到队列中
taskQueue.add(counter);
System.out.println("生产序号: " + counter);
counter++;
//唤醒正在等待的消费者,但是消费者是不是能获取到资源,由系统调度。
taskQueue.notifyAll();
}
}
catch (InterruptedException ex)
{
ex.printStackTrace();
}
}
}
}
package 信号量操作;
import java.util.List;
public class Consumer implements Runnable{
private final List<Integer> taskQueue ;
//初始化
public Consumer(List<Integer> sharedQueue){
this.taskQueue = sharedQueue;
}
public void run()
{
while (true)
{
try
{
synchronized (taskQueue)
{
//当队列为空的时候,消费者进程就要进行等待
while (taskQueue.isEmpty())
{
System.out.println("队列为空, " + Thread.currentThread().getName() +
"处于等待 , 大小: " + taskQueue.size());
taskQueue.wait();
}
//休眠1秒
Thread.sleep(3000);
//移除第一次出现的元素,返回true
int i = (Integer) taskQueue.remove(0);
System.out.println("消费序号: " + i);
//全部唤醒
taskQueue.notifyAll();
}
} catch (InterruptedException ex)
{
ex.printStackTrace();
}
}
}
}
package 信号量操作;
import java.util.ArrayList;
import java.util.List;
public class Test {
public static void main(String[] args) throws InterruptedException {
//共享资源
List<Integer> taskQueue = new ArrayList<Integer>();
//设置最大容量为5
int MAX_CAPACITY = 5;
//创建生产者线程
Thread producer = new Thread(new Producer(taskQueue,MAX_CAPACITY),"producer");
//创建消费者线程
Thread consumer = new Thread(new Consumer(taskQueue),"consumer");
//开启线程
consumer.start();
Thread.sleep(2000);
producer.start();
}
}