public class ProducerConsumer{
public static void main(String[] args){
SyncStack ss = new SyncStack();
Producer p = new Producer(ss);
Producer pp = new Producer(ss);
Consumer c = new Consumer(ss);
new Thread(pp).start();
new Thread(p).start();
new Thread(c).start();
}
}class WoTou{
int id;
WoTou(int id){
this.id=id;
}
public String toString(){
return "WoTou:"+id;
}
}class SyncStack{
int index = 0;
WoTou[] arrwt=new WoTou[6];

public synchronized void push(WoTou wt){
while(index==arrwt.length){
try{
this.wait();
}catch(InterruptedException e){
System.out.println(e);
}
}
this.notifyAll();
arrwt[index]=wt;
index++;

} public synchronized WoTou pop(){
while(index==0){
try{
this.wait();
}catch(InterruptedException e){
System.out.println(e);
}
}
this.notifyAll();
index--;
return arrwt[index];
}
}class Producer implements Runnable{
SyncStack ss=null;
Producer(SyncStack ss){
this.ss=ss;
}
public void run(){
for(int i=0;i<10;i++){
WoTou wt = new WoTou(i);
ss.push(wt);
System.out.println("生产:"+wt);
try {
Thread.sleep((int)(Math.random() * 200));
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}class Consumer implements Runnable{
SyncStack ss = null;
Consumer(SyncStack ss){
this.ss=ss;
}
public void run(){
for(int i=0;i<10;i++){
WoTou wt=ss.pop();
System.out.println("消费:"+wt);
try {
Thread.sleep((int)(Math.random() * 200));
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
当SyncStack类里的WoTou[] arrwt=new WoTou[6] 元素小于10就会死锁,好想是一直被 wait 着。
为什么notifyAll不会唤醒pop()方法。
是哪里的原因,始终找不到。这是尚学堂视频里的例子。比对后也找不到,不明白。
请大家帮忙找找原因。

解决方案 »

  1.   

    LZ搞两个线程去放东西,一个线程去读,读10次完,消费者线程结束了,ss又是满的,于是生产者就在那等呀等。再取比对看看吧
      

  2.   

    两个生产线程一个消费线程,也就是说会生产20次,消费10次,当消费线程结束后就不会触发pop,所有生产线成满的时候就会一直停留在wait
      

  3.   

    不是很明白了,this.notifyAll()不是能唤醒吗,唤醒后消费者又开始取了。不应该停的啊。
      

  4.   

    懂了。懂了。懂了。
    我再加一个消费者线程,或者 消费者的for变成20 让取的次数与生产的次数相当就可以了。