2016-04-09 5 views
4

私はRunクラスを持っています。シンプルで、印刷し、スリープしてから印刷します。スレッドが実行可能状態のときにオブジェクトがロックされないのはなぜですか?

public class Run implements Runnable { 

    @Override 
    public void run() { 
     System.out.println("START RUN"); 
     try { 
      Thread.sleep(50); 
     } catch (InterruptedException e) { 
      e.printStackTrace(); 
     } 
     System.out.println("FINISH RUN"); 
    } 
} 

今、私はテストを書いています。

public static synchronized void main(String[] args) throws InterruptedException { 

     Run r = new Run(); 
     Thread t = new Thread(r, "TEST"); 
     t.start(); 

     // EXECYTE THE CODE WHULE THREAD "TEST" IS RUNNABLE 
     synchronized (t) { 
      System.out.println(t.getState()); 
      t.wait(); 
     } 
     System.out.println("Y"); 

     // SLEEP THREAD "TEST" TO BE EXECUTED DURING THE TIME 
     Thread.sleep(100); 
     synchronized (t) { 
      System.out.println(t.getState()); 
      t.wait(); 
     } 
     System.out.println("Y2"); 
    } 

質問1:スレッド "TEST" を実行している間、私は(待機するようにしてみてください)。 現在のところ、スレッドステータスは "RUNNABLE"です。このステータスのためにではない待ち、私はなぜ理解できないのですか?ステータスが "TERMINATED"または "NEW"の場合はwait()が働きます。 t.start()を削除した場合、スレッドステータスは "NEW"になりますので、waitも機能します。何が起こるか教えていただけますか?

OUTPUT:これはかなり悪い文書化されて

START RUN 
RUNNABLE 
FINISH RUN 
Y 
TERMINATED` 
+0

簡単な質問: 't.wait()'は何をしていると思いますか? – biziclop

+0

これは、スレッドが開始されるときの状態のみを示します。 'Thread.sleep'は何もロックしません。 –

+0

別のスレッドがnotifyまたはnotifyAllを呼び出すまで、現在のスレッドを待機させます。 t.wait()が実行されると、まずスレッドはスリープ状態になり、待機しません。スレッドが実行された後に、スレッドが実行された後 – grep

答えて

10

Thread#join(long)のjavadocの状態

スレッドが終了するとthis.notifyAllメソッドが呼び出されます。 アプリケーションでは、wait,notifynotifyAllThreadインスタンスでは使用しないことをお勧めします。

具体的には現在行っていることをしないと言っています。つまり、Threadオブジェクトには​​があり、同じオブジェクトにはwaitが呼び出されます。

synchronized (t) { 
    System.out.println(t.getState()); 
    t.wait(); 
} 

コードの現在の実行中です。 TESTスレッドがスリープしている間、メインスレッドは上記のt.wait()呼び出しに達します。 TESTはウェイクアップして終了します。終了すると、notifyAllt.wait()からメインスレッドを起動します。

メインスレッドが2番目のt.wait()に達すると、プログラムには何も残っておらず、プログラムが起動するだけです。


言うことをすべてこの:ためThreadオブジェクトモニターを使用しないでください。

+0

そして、 "推奨される"ことによって、明快になるために、 "決してこれを実行しない"という意味です。 :)本当にしないでください。ただしないでください。 – biziclop

+0

私は分かりません。スレッドが終了した場合、または新しいスレッドがハングした場合 – grep

+0

終了したか、新しい(起動していない)場合は、 'notifyAll'を呼び出さないので、最初の' t.wait() 'からメインスレッドを起動するものはありません。 – Savior