2014-08-29 89 views
-1

为什么wait()在同步块内?我的意思是,只有一个线程将进入同步块,那么另一个线程如何执行wait()指令?为什么在里面等待同步?

+2

哪'synchronized'块你在说什么?你的问题真的不清楚(也很广泛)...... – BackSlash 2014-08-29 12:49:16

+0

没有任何答案,无论是在这里还是在副本中,都提到了一个典型的原因:“notifyAll”将会是一团糟,无需在继续之前重新获得锁定。 – 2014-08-29 13:22:18

+0

这是因为在你等待某件事之前,你必须确定事情还没有发生。你必须确保它不会在你等待时发生。所以你必须持有一个锁来等待某件事 - 这个锁可以保护你等待状态改变的东西。 – 2016-03-30 09:35:59

回答

2
  1. 同步关键字用于独占访问。
  2. 要使方法同步,只需将synchronized关键字添加到其声明中即可。然后,同一对象上的同步方法的任何两次调用都可以相互交错。
  3. 同步语句必须指定提供内部锁定的对象。使用同步(this)时,您必须避免同步其他对象方法的调用。
  4. wait()通知调用线程放弃监视器并进入休眠状态,直到某个其他线程进入相同的监视器并调用notify()。
  5. notify()唤醒在同一个对象上调用wait()的第一个线程。

例子:

public class ThreadA { 
    public static void main(String[] args){ 
     ThreadB b = new ThreadB(); 
     b.start(); 

     synchronized(b){ 
      try{ 
       System.out.println("Waiting for b to complete..."); 
       b.wait(); 
      }catch(InterruptedException e){ 
       e.printStackTrace(); 
      } 

      System.out.println("Total is: " + b.total); 
     } 
    } 
} 

class ThreadB extends Thread{ 
    int total; 
    @Override 
    public void run(){ 
     synchronized(this){ 
      for(int i=0; i<100 ; i++){ 
       total += i; 
      } 
      notify(); 
     } 
    } 
} 

得到它:http://www.programcreek.com/2009/02/notify-and-wait-example/

+0

为什么'synchronized(this)'在'ThreadB'中被调用?不仅线程本身调用运行,并且没有其他线程? – Artemkller545 2014-08-29 12:56:51

+0

当我尝试运行没有这个同步块,我得到了一个java.lang.IllegalMonitorStateException,这很有趣。当通过b同步threadA时,它需要保证notify()也被同步,或者其他实例可以调用notify。 – 2014-08-29 13:17:14

0
Why is wait() inside of a synchronized block? 

因为线程需要有你呼吁wait()对象的监视器,在一个synchronized方法的情况下,this对象。

I mean, only one thread will enter the synchronized block, so how can the other 
thread execute the wait() instruction? 

它不能,只有同步块内的线程可以执行wait(),允许其他线程进入同步块。

+0

“[foo。]为什么[需要]在[synchronized(foo)]内部等待?”你基本上说,“因为它需要。” _why_会更好的回答。完整的答案对于这个空间来说太大了,但简而言之, 'foo.wait()'的调用者应该等待一些明确的,可测试的条件,并且为了避免“丢失的通知”,可以测试或改变条件的每个代码块(包括服务员)应该同步同一把锁。 Java不能强制代码块是同步的,但是它对等待的块()和通知()的块是这样做的。 – 2014-08-29 13:19:25