Thread--生产者消费者假死分析
1 package p_c_allWait; 2 3 public class ValueObject { 4 5 public static String value = ""; 6 7 }
1 package p_c_allWait; 2 3 public class P { 4 5 private String lock; 6 7 public P(String lock) { 8 super(); 9 this.lock = lock; 10 } 11 12 public void setValue() { 13 try { 14 synchronized (lock) { 15 while(!ValueObject.value.equals("")) { 16 System.out.println("生产者 " + Thread.currentThread().getName() + " WAITING 了"); 17 lock.wait(); 18 } 19 System.out.println("生产者 " + Thread.currentThread().getName() + " RUNNABLE 了"); 20 String value = System.currentTimeMillis() + "_" + System.nanoTime(); 21 ValueObject.value = value; 22 lock.notify(); 23 } 24 } catch (Exception e) { 25 // TODO: handle exception 26 e.printStackTrace(); 27 } 28 } 29 30 }
1 package p_c_allWait; 2 3 public class C { 4 5 private String lock; 6 7 public C(String lock) { 8 super(); 9 this.lock = lock; 10 } 11 12 public void getValue() { 13 try { 14 synchronized (lock) { 15 while(ValueObject.value.equals("")) { 16 System.out.println("消费者 " + Thread.currentThread().getName() + " wating 了"); 17 lock.wait(); 18 } 19 System.out.println("消费者 " + Thread.currentThread().getName() + " RUNNABLE 了"); 20 ValueObject.value = ""; 21 lock.notify(); 22 } 23 } catch (Exception e) { 24 // TODO: handle exception 25 e.printStackTrace(); 26 } 27 } 28 29 }
1 package p_c_allWait; 2 3 public class ThreadP extends Thread { 4 5 private P p; 6 7 public ThreadP(P p) { 8 super(); 9 this.p = p; 10 } 11 12 @Override 13 public void run() { 14 while(true) { 15 p.setValue(); 16 } 17 } 18 19 }
1 package p_c_allWait; 2 3 public class ThreadC extends Thread { 4 5 private C c; 6 7 public ThreadC(C c) { 8 super(); 9 this.c = c; 10 } 11 12 @Override 13 public void run() { 14 while(true) { 15 c.getValue(); 16 } 17 } 18 19 20 21 }
1 package p_c_allWait; 2 3 public class Run { 4 5 public static void main(String[] args) { 6 String lock = ""; 7 P p = new P(lock); 8 C r = new C(lock); 9 ThreadP[] pThread = new ThreadP[2]; 10 ThreadC[] cThread = new ThreadC[2]; 11 for(int i=0; i<2; i++) { 12 pThread[i] = new ThreadP(p); 13 pThread[i].setName("生产者 " + (i+1)); 14 cThread[i] = new ThreadC(r); 15 cThread[i].setName("消费者 " + (i+1)); 16 pThread[i].start(); 17 cThread[i].start(); 18 } 19 } 20 21 }
notify每次只唤醒一个线程。
而notify唤醒线程是随机的,并不能保证每次唤醒的是异类线程,即生产者唤醒的可能是另一个生产者的线程。