Java多线程编程#线程等待机制
1、最佳的模型是:生产者-消费者
package com.boonya.multithread.explain;/** ============================================== * 文件:ProducerAndConsumer.java * 描述:生产者--消费者 [生产者生产了之后消费者才能消费] * 注:引入了等待通知(wait/notify)机制如下: 1、在生产者没有生产之前,通知消费者等待;在生产者生产之后,马上通知消费者消费。 2、在消费者消费了之后,通知生产者已经消费完,需要生产。 * ============================================ */ public class ProducerAndConsumer { public static void main(String argv[]){ ShareData s = new ShareData(); new Consumer(s).start(); new Producer(s).start(); } }class ShareData{ private char c; // 通知变量 private boolean writeable = true; // ------------------------------------- // 需要注意的是:在调用wait()方法时,需要把它放到一个同步段里,否则将会出现 // "java.lang.IllegalMonitorStateException: current thread not owner"的异常。 // ------------------------------------- public synchronized void setShareChar(char c){ if (!writeable){ try{ // 未消费等待 wait(); }catch(InterruptedException e){} } this.c = c; // 标记已经生产 writeable = false; // 通知消费者已经生产,可以消费 notify(); } public synchronized char getShareChar(){ if (writeable){ try{ // 未生产等待 wait(); }catch(InterruptedException e){} } // 标记已经消费 writeable = true; // 通知需要生产 notify(); return this.c; } } // 生产者线程 class Producer extends Thread{ private ShareData s; Producer(ShareData s){ this.s = s; } public void run(){ for (char ch = 'A'; ch <= 'Z'; ch++){ try{ Thread.sleep((int)Math.random() * 400); }catch(InterruptedException e){} // 生产 s.setShareChar(ch); System.out.println(ch + " producer by producer."); } } } // 消费者线程 class Consumer extends Thread{ private ShareData s; Consumer(ShareData s){ this.s = s; } public void run(){ char ch; do{ try{ Thread.sleep((int)Math.random() * 400); }catch(InterruptedException e){} // 消费 ch = s.getShareChar(); System.out.println(ch + " consumer by consumer."); }while(ch != 'Z'); } }
package com.boonya.multithread.explain;/**=================================== * 文件:LetOneThreadSleepAfterAnotherReady.java * 描述:等待一个线程的结束的两种方法 * ==================================== */ public class LetOneThreadSleepAfterAnotherReady { class MyTaskThread extends Thread{public MyTaskThread(){}@Overridepublic void run() { for (int count = 1,row = 1; row < 20; row++,count++) { for (int i = 0; i < count; i++) { System.out.print('*'); } System.out.println(); } } } // 第一种方法:不断查询第一个线程是否已经终止,如果没有,则让主线程睡眠一直到它终止为止 // 即:while/isAlive/sleep public void Method1(){ MyTaskThread th1 = new MyTaskThread(); MyTaskThread th2 = new MyTaskThread(); // 执行第一个线程 th1.start(); // 不断查询第一个线程的状态 while(th1.isAlive()){ try{ Thread.sleep(100); }catch(InterruptedException e){ } } //第一个线程终止,运行第二个线程 th2.start(); } // 第二种方法:join() public void Method2(){ MyTaskThread th1 = new MyTaskThread(); MyTaskThread th2 = new MyTaskThread(); // 执行第一个线程 th1.start(); try{ th1.join(); }catch(InterruptedException e){ } // 执行第二个线程 th2.start(); } public static void main(String[] args) { LetOneThreadSleepAfterAnotherReady mythread=new LetOneThreadSleepAfterAnotherReady();// mythread.Method1(); mythread.Method2();}}1 楼 zjuttsw 昨天 提一点意见: