WEB开发网
开发学院软件开发Java Java 多线程同步问题的探究(四、协作,互斥下的协... 阅读

Java 多线程同步问题的探究(四、协作,互斥下的协作——Java多线程协作(wait、notify、notifyAll))

 2010-05-14 00:00:00 来源:WEB开发网   
核心提示:Java监视器支持两种线程:互斥和协作,前面我们介绍了采用对象锁和重入锁来实现的互斥,Java 多线程同步问题的探究(四、协作,互斥下的协作——Java多线程协作(wait、notify、notifyAll)),这一篇中,我们来看一看线程的协作,判断条件状态,以便决定是否继续进入等待状态或者执行监视区域,举个例子:有一

Java监视器支持两种线程:互斥和协作。

前面我们介绍了采用对象锁和重入锁来实现的互斥。这一篇中,我们来看一看线程的协作。

举个例子:有一家汉堡店举办吃汉堡比赛,决赛时有3个顾客来吃,3个厨师来做,一个服务员负责协调汉堡的数量。为了避免浪费,制作好的汉堡被放进一个能装有10个汉堡的长条状容器中,按照先进先出的原则取汉堡。如果容器被装满,则厨师停止做汉堡,如果顾客发现容器内的汉堡吃完了,就可以拍响容器上的闹铃,提醒厨师再做几个汉堡出来。此时服务员过来安抚顾客,让他等待。而一旦厨师的汉堡做出来,就会让服务员通知顾客,汉堡做好了,让顾客继续过来取汉堡。

这里,顾客其实就是我们所说的消费者,而厨师就是生产者。容器是决定厨师行为的监视器,而服务员则负责监视顾客的行为。

在JVM中,此种监视器被称为等待并唤醒监视器。

在这种监视器中,一个已经持有该监视器的线程,可以通过调用监视对象的wait方法,暂停自身的执行,并释放监视器,自己进入一个等待区,直到监视器内的其他线程调用了监视对象的notify方法。当一个线程调用唤醒命令以后,它会持续持有监视器,直到它主动释放监视器。而这之后,等待线程会苏醒,其中的一个会重新获得监视器,判断条件状态,以便决定是否继续进入等待状态或者执行监视区域,或者退出。

请看下面的代码:

   1. public class NotifyTest { 
   2.     private  String flag = "true"; 
   3.  
   4.     class NotifyThread extends Thread{ 
   5.         public NotifyThread(String name) { 
   6.             super(name); 
   7.         } 
   8.         public void run() {      
   9.             try { 
  10.                 sleep(3000);//推迟3秒钟通知 
  11.             } catch (InterruptedException e) { 
  12.                 e.printStackTrace(); 
  13.             } 
  14.              
  15.                 flag = "false"; 
  16.                 flag.notify(); 
  17.         } 
  18.     }; 
  19.  
  20.     class WaitThread extends Thread { 
  21.         public WaitThread(String name) { 
  22.             super(name); 
  23.         } 
  24.  
  25.         public void run() { 
  26.              
  27.                 while (flag!="false") { 
  28.                     System.out.println(getName() + " begin waiting!"); 
  29.                     long waitTime = System.currentTimeMillis(); 
  30.                     try { 
  31.                         flag.wait(); 
  32.                     } catch (InterruptedException e) { 
  33.                         e.printStackTrace(); 
  34.                     } 
  35.                     waitTime = System.currentTimeMillis() - waitTime; 
  36.                     System.out.println("wait time :"+waitTime); 
  37.                 } 
  38.                 System.out.println(getName() + " end waiting!"); 
  39.              
  40.         } 
  41.     } 
  42.  
  43.     public static void main(String[] args) throws InterruptedException { 
  44.         System.out.println("Main Thread Run!"); 
  45.         NotifyTest test = new NotifyTest(); 
  46.         NotifyThread notifyThread =test.new NotifyThread("notify01"); 
  47.         WaitThread waitThread01 = test.new WaitThread("waiter01"); 
  48.         WaitThread waitThread02 = test.new WaitThread("waiter02"); 
  49.         WaitThread waitThread03 = test.new WaitThread("waiter03"); 
  50.         notifyThread.start(); 
  51.         waitThread01.start(); 
  52.         waitThread02.start(); 
  53.         waitThread03.start(); 
  54.     } 
  55.  
  56. } 

1 2 3 4 5 6  下一页

Tags:Java 线程 同步

编辑录入:爽爽 [复制链接] [打 印]
赞助商链接