java信号量PV操作 解决生产者-消费者问题

时间:2022-02-14 00:31:40
package test1;
/**
* 该例子演示生产者和消费者的问题(设只有一个缓存空间、一个消费者和一个生产者)
* MySystem类定义了缓冲区个数以及信号量
* @author HYY
*/
public class MySystem {
// 缓存区的个数
private int count = 0; // s1 s2为信号量
private MyInt s1 = new MyInt();// 生产者信号量,初始值为0->表示没有可以存放产品的空间
private MyInt s2 = new MyInt();// 消费者信号量,初始值为0->表示没有可以消费的产品 public int getCount() {
return count;
} public void setCount(int count) {
this.count = count;
} public MyInt getS1() {
return s1;
} public void setS1(MyInt s1) {
this.s1 = s1;
} public MyInt getS2() {
return s2;
} public void setS2(MyInt s2) {
this.s2 = s2;
} // p操作
public synchronized void p(MyInt s) {
s.setI(s.getI() - 1);
if (s.getI() < 0) {
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
} // v操作
public synchronized void v(MyInt s) {
s.setI(s.getI() + 1);
if (s.getI() <= 0) {
this.notify();
}
} public static void main(String[] args) {
System.out.println("生产者-消费者系统初始化,当前信号量都为0,产品数为0.");
MySystem mySystem = new MySystem();
new Thread(new Producer(mySystem)).start();
new Thread(new Consumer(mySystem)).start();
}
} class MyInt {
private int i = 0; public int getI() {
return i;
} public void setI(int i) {
this.i = i;
} } // 生产者
class Producer implements Runnable { private MySystem mySystem; public Producer() {
} public Producer(MySystem mySystem) {
this.mySystem = mySystem;
} @Override
public void run() {
System.out.println("生产者初始化完毕。");
while (true) {
mySystem.setCount(mySystem.getCount() + 1);
System.out.println("生产一个产品,将产品送入缓冲区,当前产品数量:" + mySystem.getCount());
// 设置信号量,通知消费者消费
mySystem.v(mySystem.getS2());
// 设置信号量,检测是否可以继续生产
mySystem.p(mySystem.getS1()); // 休息
try {
Thread.sleep(500);
} catch (InterruptedException e) {
}
}
} } // 消费者
class Consumer implements Runnable { private MySystem mySystem; public Consumer() {
} public Consumer(MySystem mySystem) {
this.mySystem = mySystem;
} @Override
public void run() {
System.out.println("消费者初始化完毕。");
while (true) {
// 设置信号量,检测是否允许消费
mySystem.p(mySystem.getS2());
mySystem.setCount(mySystem.getCount() - 1);
System.out.println("消费一个产品,当前产品数量:" + mySystem.getCount() + "。");
// 设置信号量,通知生产者生产
mySystem.v(mySystem.getS1()); // 休息
try {
Thread.sleep(500);
} catch (InterruptedException e) {
}
}
}
}