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

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© wangning9130 中级黑马   /  2013-10-24 23:00  /  1699 人查看  /  6 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

各位,关于Thread中的。。。知道有好几个线程,并且 线程可以wait();sleep();还有notify()和notifyall();
sleep 是线程休眠。
notify()可以唤醒wait中的线程,
notify()可以唤醒全部线程。  那么使用notifyall()唤醒全部线程,对正在sleep中的线程有效果吗?

评分

参与人数 1技术分 +1 收起 理由
杨增坤 + 1

查看全部评分

6 个回复

倒序浏览
notifyall()唤醒的是等待的线程,不会唤醒睡眠的线程。
wait的线程是放弃的资格!
sleep的线程是有执行资格,但是没有执行权
回复 使用道具 举报
notify对sleep没有效果。
程序使用wait()时,是让当前线程进入线程等待池中进行等待,让出了系统资源,释放了锁,使得其他线程可以使用同步控制块。这时候就需要notify()或notifyAll()来唤醒等待池中的线程。
sleep()方法是当前线程休眠若干时间,并不让出系统资源,若干时间过后会自动醒来。它是Thread类的方法,而wait()是Object类的方法

评分

参与人数 1技术分 +1 收起 理由
乔兵 + 1

查看全部评分

回复 使用道具 举报
3楼说的对!
回复 使用道具 举报
本帖最后由 黄小贝 于 2013-10-25 00:18 编辑

好吧,我觉得你应该事先谷歌才来问问题的,这样来混技术分不合适~让专业的来给你分析
Synchronization is achieved using monitors. Every object can have a monitor associated with it, so any object can synchronize blocks. Before a synchronized block can be entered, a thread needs to gain ownership of the monitor for that block. Once the thread has gained ownership of the monitor, no other thread synchronized on the same monitor can gain entry to that block (or any other block or method synchronized on the same monitor). The thread owning the monitor gets to execute all the statements in the block, and then automatically releases ownership of the monitor on exiting the block. At that point, another thread waiting to enter the block can acquire ownership of the monitor.

首先你需要明白synchronized的原理,它是由monitors实现的,每个对象都有一个monitors,所以synchronized()的括号里面可以填任意对象,当一个线程试图进入一个synchronized代码块的时候,必须得到这个代码块的monitors,一旦有一个线程得到了这个代码块的monitors后,其他所有在同一monitors下的线程都必须等待,获得monitors的线程执行完代码后会自动释放monitors的所有权,好让其他线程进入

很好,概念扯完了,给你看一个例子


让我能完成一个小例子,两个线程,对 n 进行操作,一个从从 1 打印到5 一个从 5打印到 1
  1. package com.yellow.chapteOne;

  2. public class Test {

  3.         private static int n = 0;

  4.         private static boolean flag = true;

  5.         public static void main(String[] args) {

  6.                 final Object lock = new Object();

  7.                 Thread thread1 = new Thread(new Runnable() {

  8.                         @Override
  9.                         public void run() {
  10.                                 synchronized (lock) {
  11.                                         while (true) {
  12.                                                 if (flag != true) {
  13.                                                         try {
  14.                                                                 lock.wait();
  15.                                                         } catch (InterruptedException e) {
  16.                                                                 e.printStackTrace();
  17.                                                         }
  18.                                                 }
  19.                                                 for (int i = 0; i < 5; i++) {
  20.                                                         System.out.println(n++);
  21.                                                         try {
  22.                                                                 Thread.sleep(500);
  23.                                                         } catch (InterruptedException e) {
  24.                                                                 e.printStackTrace();
  25.                                                         }
  26.                                                 }
  27.                                                 flag = false;
  28.                                                 lock.notify();
  29.                                         }
  30.                                 }
  31.                         }
  32.                 });
  33.                
  34.                 Thread thread2 = new Thread(new Runnable() {

  35.                         @Override
  36.                         public void run() {
  37.                                 synchronized (lock) {
  38.                                         while (true) {
  39.                                                 if (flag != false) {
  40.                                                         try {
  41.                                                                 lock.wait();
  42.                                                         } catch (InterruptedException e) {
  43.                                                                 e.printStackTrace();
  44.                                                         }
  45.                                                 }
  46.                                                 for (int i = 0; i < 5; i++) {
  47.                                                         System.out.println(n--);
  48.                                                         try {
  49.                                                                 Thread.sleep(500);
  50.                                                         } catch (InterruptedException e) {
  51.                                                                 e.printStackTrace();
  52.                                                         }
  53.                                                 }
  54.                                                 flag = true;
  55.                                                 lock.notify();
  56.                                         }
  57.                                 }
  58.                         }
  59.                 });
  60.                
  61.                 thread1.start();
  62.                 thread2.start();

  63.         }

  64. }
复制代码
这个例子里面的synchronized的对象是final Object lock = new Object();  因为两段synchronized代码都在lockmonitors下,so,他们不可能能够同时执行


现在就到了wait和notify的作用了,看看源码注释

wait()的
  1.   /**
  2.      * The current thread must own this object's monitor. The thread   当前线程必须拥有这个对象的monitor
  3.      * releases ownership of this monitor and waits until another thread  并且释放自己对monitor的所属权
  4.      * notifies threads waiting on this object's monitor to wake up   直到另一个线程执行notifies 或者 notifyAll
  5.      * either through a call to the <code>notify</code> method or the
  6.      * <code>notifyAll</code> method. The thread then waits until it can 这个线程会一直等待直到重新获得monitor的所有权然后继续执行
  7.      * re-obtain ownership of the monitor and resumes execution.
  8.      * <p>
  9.      * As in the one argument version, interrupts and spurious wakeups are
  10.      * possible, and this method should always be used in a loop:  正是因为执行这个方法的前提是必须获得monitor
复制代码
notify()的
  1.   /**
  2.      * Wakes up a single thread that is waiting on this object's   唤醒其他在等这个对象的monitor的线程
  3.      * monitor. If any threads are waiting on this object, one of them   如果有很多线程都在等这个monitor,随机选一个~~
  4.      * is chosen to be awakened. The choice is arbitrary and occurs at 好吧,所以这很不科学,想唤醒所有的线程,请用notifyAll
  5.      * the discretion of the implementation. A thread waits on an object's
  6.      * monitor by calling one of the <code>wait</code> methods.
  7.      * <p>
  8.      * The awakened thread will not be able to proceed until the current
  9.      * thread relinquishes the lock on this object. The awakened thread will
  10.      * compete in the usual manner with any other threads that might be
  11.      * actively competing to synchronize on this object; for example, the
  12.      * awakened thread enjoys no reliable privilege or disadvantage in being
  13.      * the next thread to lock this object.
  14.      * <p>
  15.      * This method should only be called by a thread that is the owner
  16.      * of this object's monitor. A thread becomes the owner of the
  17.      * object's monitor in one of three ways:
  18.      * <ul>
  19.      * <li>By executing a synchronized instance method of that object.
  20.      * <li>By executing the body of a <code>synchronized</code> statement
  21.      *     that synchronizes on the object.
  22.      * <li>For objects of type <code>Class,</code> by executing a
  23.      *     synchronized static method of that class.
  24.      * </ul>
  25.      * <p>
  26.      * Only one thread at a time can own an object's monitor.
  27.      *
  28.      * @exception  IllegalMonitorStateException  if the current thread is not
  29.      *               the owner of this object's monitor.
  30.      * @see        java.lang.Object#notifyAll()
  31.      * @see        java.lang.Object#wait()
  32.      */
复制代码
至于 sleep()  那只是当当前执行的线程停止...
  1. /**        
  2.      * Causes the currently executing thread to sleep (temporarily cease
  3.      * execution) for the specified number of milliseconds, subject to
  4.      * the precision and accuracy of system timers and schedulers. The thread   没有失去monitors的所有权
  5.      * does not lose ownership of any monitors.
  6.      *
  7.      * @param      millis   the length of time to sleep in milliseconds.
  8.      * @exception  InterruptedException if any thread has interrupted
  9.      *             the current thread.  The <i>interrupted status</i> of the
  10.      *             current thread is cleared when this exception is thrown.
  11.      * @see        Object#notify()
  12.      */
  13.     public static native void sleep(long millis) throws InterruptedException;
复制代码
好啦~~总结一下,sleep是停止当前线程,没有失去monitors,wait是释放monitors让其他在同一个monitors下的线程有机会执行然后进行等待,notify是去线程执行完了去唤醒其他在等待的线程

现在懂了吧~~版主不加分我就再也不相信爱情了

评分

参与人数 1技术分 +1 收起 理由
乔兵 + 1 感谢分享知识。。。

查看全部评分

回复 使用道具 举报
直接点。只回答你的问题吧:notifyall对sleep无效,sleep是有参数限定的,当参数时间执行完毕就自动苏醒过来(sleep不释放 monitor )。
回复 使用道具 举报
To 金牌黑马 2013-10-27 16:05:28
7#
楼主你好,如果问题已解决请将帖子状态修改为提问结束,
如果未解决请继续追问,谢谢合作
修改方法请看解释帖:http://bbs.itheima.com/thread-89313-1-1.html
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马