求助,关于模仿生产者消费者的问题 本帖最后由 hzy2121211 于 2010-03-02 22:10:50 编辑 解决方案 » 免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货 package Thread;public class TwoThread { public static void main(String[] args) { Queue q=new Queue ();//new出一个q:后面的两个线程都是用的同一个q,保证一个put一个get Producer p=new Producer (q);//让new出的p去往q里面put Customer c=new Customer (q);//让new出的c从q中get p.start();//p和q开始的顺序并不报错 c.start(); }}class Producer extends Thread{ Queue q; public Producer(Queue q) { this.q=q;//给成员变量赋值,再一调运q的put方法 } @Override public void run() { for (int i = 0; i < 10; i++) { q.put(i);//此处只是让q去put 10次 System.out.println("Producer put "+i);//并且输出本次放的是第几杯 } }}class Customer extends Thread{ Queue q; public Customer(Queue q) { this.q=q;//给成员变量赋值,再一调运q的get方法 } @Override public void run() { while (true) {//死循环:只要q里面有,就去get //get方法有返回值,返回值就是producer所put的数量 //此处也不需要去考虑是第几杯 //在Queue中的value解决可这一问题: //put中的I赋给value,get方法有返回值就value的值 System.out.println("Customer get "+q.get()); //如果循环完了,就跳出循环,否则线程不会自己结束 if (q.value==9) { break; } } }}class Queue{ int value; boolean bFull=false; public synchronized void put (int i)//在producer中的put方法中就是将其I传进来 { if (!bFull) {//条件为真(如果没满,就倒水) value=i;//给value赋值,现在有几杯水 bFull=true;//满了 notify();//唤醒其他线程(让customer去get) } try { wait();//告诉customer去get后自己等待customer的get结束 } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public synchronized int get() { if (!bFull) {//如果没满就等待,如果满了就不进 **这就是为什么main里面谁先开始不报错的原因** //get和put方法中的if条件判断起到了至关重要的作用 try { wait(); } catch (InterruptedException e) { e.printStackTrace(); } } bFull =false;//赋值为没满 notify();//唤醒producer去put return value;//get的返回值就是put的时候给value赋的值 }} public class ProducerConsumer { static SyncStack ss = new SyncStack(); public static void main(String[] args) { // TODO Auto-generated method stub Producer p = new Producer(ss); Consumer c = new Consumer(ss); Thread t1 = new Thread(p); Thread t2 = new Thread(c); t1.start(); t2.start(); }}// 这个是生产出来的产品WoTou(窝头)class WoTou { int id; WoTou(int id) { this.id = id; } public String toString() { return "WoTou" + id; }}// 这个是存放的产品的容器,有点模拟栈的形式class SyncStack { static int index = 0; // 标记当前产品的位置,或者产品数量 WoTou[] wtArr = new WoTou[20]; // 容器容量是20 // 把产品放进容器的方法 public synchronized void produce(WoTou w) { if (index == 20) { try { this.wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } else { this.notify(); } System.out.println("产: " + index); wtArr[index++] = w; ; // 生产完一个产品后,标记往上移动 } // 把产品从容器拿出来的办法 public synchronized WoTou consume() { if (index == 0) { try { this.wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } else { this.notify(); } System.out.println("取: " + index); // 取出来后,标记往下移 return wtArr[--index]; }}// 生产者,就是把产品放进容器class Producer implements Runnable { SyncStack ss; Producer(SyncStack ss) { this.ss = ss; } public void run() { int i = 0; // 为了能让生产不断生产,我添加了这个while while (true) { ss.produce(new WoTou(i));// System.out.println("生产 " + ss.wtArr[ss.index] + ", 还有 "// + ss.index + " 个产品"); i++; } }}// 消费者,把产品从容器拿出来class Consumer implements Runnable { SyncStack ss; Consumer(SyncStack ss) { this.ss = ss; } public void run() { while (true) { // 为了能让生产不断生产,我添加了这个while ss.consume();// System.out.println("消费 " + ss.wtArr[ss.index] + ",还有" + ss.index// + "个产品"); } }} 把上面的产和取的方法用下面替换就是你想要的了:public synchronized void produce(WoTou w) { if (index == 20) { try { this.wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } else { this.notify(); } System.out.println("产: " + wtArr[index] + "还有: " + index + "个"); wtArr[index++] = w; ; // 生产完一个产品后,标记往上移动 } // 把产品从容器拿出来的办法 public synchronized WoTou consume() { if (index == 0) { try { this.wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } else { this.notify(); }// System.out.println("取: " + index); System.out.println("取: " + wtArr[index - 1] + "还有: " + (index - 1) + "个"); // 取出来后,标记往下移 return wtArr[--index]; } 在Linux上远程部署Java应用程序的问题 大侠救命啊 询问一个字符串处理的最优方法 输入一个字符串,如何求其中字母a的个数? 紧急求助:请问如何解决JAVA socket通信时的connettion reset问题 很菜的一个问题,希望大家指教! JAVA菜鸟求教各位高手关于AWT的一个问题,多谢了 如何在MotoSDK中实现输入的文本被*掩盖! 我刚刚接触JAVA,便当头一棒。谁能帮帮我?定重谢! 问大家一个关于记事本写java的问题, java反射求助 请求帮忙分析一段多线程代码哦
public static void main(String[] args) {
Queue q=new Queue ();//new出一个q:后面的两个线程都是用的同一个q,保证一个put一个get
Producer p=new Producer (q);//让new出的p去往q里面put
Customer c=new Customer (q);//让new出的c从q中get
p.start();//p和q开始的顺序并不报错
c.start();
}
}
class Producer extends Thread
{
Queue q;
public Producer(Queue q) {
this.q=q;//给成员变量赋值,再一调运q的put方法
}
@Override
public void run() {
for (int i = 0; i < 10; i++) {
q.put(i);//此处只是让q去put 10次
System.out.println("Producer put "+i);//并且输出本次放的是第几杯
}
}
}
class Customer extends Thread
{
Queue q;
public Customer(Queue q) {
this.q=q;//给成员变量赋值,再一调运q的get方法
}
@Override
public void run() {
while (true) {//死循环:只要q里面有,就去get
//get方法有返回值,返回值就是producer所put的数量
//此处也不需要去考虑是第几杯
//在Queue中的value解决可这一问题:
//put中的I赋给value,get方法有返回值就value的值
System.out.println("Customer get "+q.get());
//如果循环完了,就跳出循环,否则线程不会自己结束
if (q.value==9) {
break;
}
}
}
}
class Queue
{
int value;
boolean bFull=false;
public synchronized void put (int i)//在producer中的put方法中就是将其I传进来
{
if (!bFull) {//条件为真(如果没满,就倒水)
value=i;//给value赋值,现在有几杯水
bFull=true;//满了
notify();//唤醒其他线程(让customer去get)
}
try {
wait();//告诉customer去get后自己等待customer的get结束
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public synchronized int get()
{
if (!bFull) {//如果没满就等待,如果满了就不进 **这就是为什么main里面谁先开始不报错的原因**
//get和put方法中的if条件判断起到了至关重要的作用
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
bFull =false;//赋值为没满
notify();//唤醒producer去put
return value;//get的返回值就是put的时候给value赋的值
}
}
// TODO Auto-generated method stub
Producer p = new Producer(ss);
Consumer c = new Consumer(ss);
Thread t1 = new Thread(p);
Thread t2 = new Thread(c);
t1.start();
t2.start();
}
}// 这个是生产出来的产品WoTou(窝头)
class WoTou {
int id; WoTou(int id) {
this.id = id;
} public String toString() {
return "WoTou" + id;
}
}// 这个是存放的产品的容器,有点模拟栈的形式
class SyncStack {
static int index = 0; // 标记当前产品的位置,或者产品数量
WoTou[] wtArr = new WoTou[20]; // 容器容量是20 // 把产品放进容器的方法
public synchronized void produce(WoTou w) {
if (index == 20) {
try {
this.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} else {
this.notify();
}
System.out.println("产: " + index);
wtArr[index++] = w;
; // 生产完一个产品后,标记往上移动
} // 把产品从容器拿出来的办法
public synchronized WoTou consume() {
if (index == 0) {
try {
this.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} else {
this.notify();
}
System.out.println("取: " + index);
// 取出来后,标记往下移
return wtArr[--index];
}
}// 生产者,就是把产品放进容器
class Producer implements Runnable { SyncStack ss; Producer(SyncStack ss) {
this.ss = ss;
} public void run() {
int i = 0; // 为了能让生产不断生产,我添加了这个while
while (true) {
ss.produce(new WoTou(i));
// System.out.println("生产 " + ss.wtArr[ss.index] + ", 还有 "
// + ss.index + " 个产品");
i++;
}
}
}// 消费者,把产品从容器拿出来
class Consumer implements Runnable {
SyncStack ss; Consumer(SyncStack ss) {
this.ss = ss;
} public void run() {
while (true) { // 为了能让生产不断生产,我添加了这个while
ss.consume();
// System.out.println("消费 " + ss.wtArr[ss.index] + ",还有" + ss.index
// + "个产品");
}
}
}
public synchronized void produce(WoTou w) {
if (index == 20) {
try {
this.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} else {
this.notify();
}
System.out.println("产: " + wtArr[index] + "还有: " + index + "个");
wtArr[index++] = w;
; // 生产完一个产品后,标记往上移动
} // 把产品从容器拿出来的办法
public synchronized WoTou consume() {
if (index == 0) {
try {
this.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} else {
this.notify();
}
// System.out.println("取: " + index);
System.out.println("取: " + wtArr[index - 1] + "还有: " + (index - 1) + "个");
// 取出来后,标记往下移
return wtArr[--index];
}