A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 王海龙2013 中级黑马   /  2013-4-8 22:27  /  1185 人查看  /  4 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

本帖最后由 王海龙2013 于 2013-4-8 23:18 编辑
  1. /**
  2. 等待唤醒机制
  3. wait();线程等待
  4. notify();唤醒其他线程
  5. notifyAll();唤醒全部线程

  6. 都使用在同步中,因为要对持有监视器(锁)的线程操作,所以要用在同步中,只有同步才有锁。

  7. 因为这些方法在操作同步线程时,都必须要标识它们所操作的线程共有的锁,只有同一锁上的被等待线程,可以被同一个锁上notify唤醒。不同锁的线程不能进行唤醒。就是只能于相同锁上才有效。
  8. 锁可以是任意对象,因此能被任意对象调用的方法只能定义在Object类中。

  9. 线程间通讯
  10. 多个线程操作同一个资源,操作动作不同(输入输出)。

  11. */
  12. class Res//要共用的资源
  13. {
  14.         String name;
  15.         String sex;
  16.         boolean flag = false;//用来改变线程状态
  17. }
  18. //输入操作线程
  19. class Input implements Runnable
  20. {
  21.         private Res r;
  22.         Input(Res r)
  23.         {
  24.                 this.r = r;
  25.         }
  26.         public void run()
  27.         {
  28.                 int x = 0;//定义输入值
  29.                 while(true)
  30.                 {
  31.                         synchronized(r)//使用唯一对象r使锁唯一
  32.                         {
  33.                                 
  34.                                 if(r.flag)
  35.                                         try{r.wait();}catch(Exception e){}//wait()有异常,实现接口中只能try
  36.                                 if(x==0)
  37.                                 {
  38.                                         r.name="mini";
  39.                                         r.sex="man";
  40.                                 }
  41.                                 else
  42.                                 {
  43.                                         r.name="五一";
  44.                                         r.sex="女";
  45.                                 }
  46.                                 x = (x+1)%2;
  47.                                 r.flag = true;//改变线程状态
  48.                                 notify();//唤醒线程
  49.                                 
  50.                         }

  51.                 }


  52.         }
  53. }
  54. //输出操作线程
  55. class Output implements Runnable
  56. {
  57.         private Res r;
  58.         Output(Res r)
  59.         {
  60.                 this.r = r;
  61.         }
  62.         public void run()
  63.         {
  64.                 while(true)
  65.                 {
  66.                         synchronized(r)
  67.                         {
  68.                                 if(!r.flag)
  69.                                         try{r.wait();}catch(Exception e){}//wait()有异常,实现接口中只能try
  70.                                 System.out.println(r.name+"---"+r.sex);
  71.                                 r.flag = false;//改变线程状态
  72.                                 notify();//唤醒线程
  73.                         }
  74.                 }
  75.         }
  76. }

  77. class InputOutputDemo
  78. {
  79.         public static void main(String[] args)
  80.         {
  81.                 //建立共用操作对象
  82.                 Res r = new Res();
  83.                 //建立输入输出操作动作对象
  84.                 Input in = new Input(r);
  85.                 Output out = new Output(r);
  86.                 //建立输入输出操作线程
  87.                 Thread t1 = new Thread(in);
  88.                 Thread t2 = new Thread(out);
  89.                 //开启输入输出线程,开始运行
  90.                 t1.start();
  91.                 t2.start();
  92.         }
  93. }
  94. /*
  95. F:\JAVA学习\java学习文档>java InputOutputDemo
  96. Exception in thread "Thread-0" java.lang.IllegalMonitorStateException
  97.         at java.lang.Object.notify(Native Method)
  98.         at Input.run(InputOutputDemo.java:56)
  99.         at java.lang.Thread.run(Thread.java:722)
  100. mini---man
  101. Exception in thread "Thread-1" java.lang.IllegalMonitorStateException
  102.         at java.lang.Object.notify(Native Method)
  103.         at Output.run(InputOutputDemo.java:87)
  104.         at java.lang.Thread.run(Thread.java:722)
  105. */
复制代码

评分

参与人数 1技术分 +1 收起 理由
滔哥 + 1

查看全部评分

4 个回复

倒序浏览
不懂是什么,编译过了,运行就挂了
回复 使用道具 举报
你代码写错了,你把notify();改成r.notify();就可以运行了,因为你使用的锁是r所以唤醒的也用r
回复 使用道具 举报
群里人说了,52和79的没有具体调用对象,应该是r.notify();
回复 使用道具 举报
真的是不小心啊,还几天没有明白
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马