2016-04-29 11 views
1

を意図したとおりのnotifyAllを動作させることはできません私はRunnableをクラスAの内部に機能してい

public void function3(){ 
    try{ 
     synchronized(lock){ 
      while(!(function2.getValue() != 0)){ 
       lock.wait(); 
      } 
      Thread.sleep(1000); 
      System.out.println(function2.getValue() + 10); 
     } 
    }catch(InterruptedException e){ 
     System.err.println(e); 
    } 
} 

I待ち状態がtrueと評価されたとしてもfunction3で出力する前に必ずfunction1で印刷するプログラムを実行してください。

function1の値を印刷する前に、function3の値を印刷するには何が必要ですか?

答えて

1

おそらくfunction1を何回か実行してfunction2の値を減らし、whileループチェックでfunction3を実行しているようです。したがって、まず、function1がprint文の前に1秒間待機している間にfunction1がprint3の前に印刷することを期待するのは完全に普通ですが、その間にfunction1は必要なことを何でも行うことができます。

第2に、より洗練された解決策は、function1の内部でfunction2の値をチェックしてから、それが== 0の場合にnotifyAll()をチェックすることです。このように、function3ではwhileループは必要ありません。 wait()を呼び出し、function1からのnotifyAll()呼び出しを待ちます。私は何を意味

: 機能1は

if(function2.getValue() == 0) 
    lock.notifyAll(); 

関数3を追加ループ

// no while loop 
lock.wait(); 

はその後はfunction1コールlock.waitに最初のif文の内部で関数3プリントを確保するために、元の質問に答えることながら削除()の後にnotifyAll()を追加し、function3の最後にnotifyAll()を追加します。

以下のコンパイル可能なクラスが示しています。

public class StackSyncProb{ 
    private volatile int function2; 
    private Object lock = new Object(); 

    public static void main(String[] args){ 
     StackSyncProb s = new StackSyncProb(3); // function2 starts at 3 
     // start function3, which waits 
     s.runFunction3(); 
     // decrement using function1 until hit 0 (in this case, 3 times) 
     for(int i = 0; i < 3; i++){ 
      s.runFunction1(); 
     } 
    } 

    public StackSyncProb(int v){ 
     function2 = v; 
    } 

    public void runFunction1(){ 
     new Thread(new Run1()).start(); 
    } 

    public void runFunction3(){ 
     new Thread(new Run2()).start(); 
    } 

    public class Run1 implements Runnable{ 
     @Override 
     public void run(){ 
      function1(); 
     } 
     public void function1(){ 
      try{ 
      synchronized(lock){ 
       function2--; 
       // Use if statement to check inside function1 instead of in function3 
       if(function2 == 0){ 
        lock.notifyAll(); 
        // After notifying, wait until function3 done 
        lock.wait(); 
       } 
       System.out.println("function1: " + function2); 
      } 
      }catch(InterruptedException e){} 
     } 
    } 

    public class Run2 implements Runnable{ 
     @Override 
     public void run(){ 
      function3(); 
     } 
     public void function3(){ 
      try{ 
       synchronized(lock){ 
        // No while loop 
        lock.wait(); 
        Thread.sleep(1000); 
        System.out.println("function3: " + (function2 + 10)); 
        // Notify function1 it can complete and print 
        lock.notifyAll(); 
       } 
      }catch(InterruptedException e){ 
       System.err.println(e); 
      } 
     } 
    } 
} 
+0

偽のウェイクアップのために、とにかくwhileループは必要ありませんか? –

+0

あなたは正しいです。私が私の答えを書いたとき、私の心を渡らなかった。あなたはまた、いくつかの他の条件、おそらく関数3で設定されたブール値に基づいてfunction1 wait()を囲むwhileループが必要になります... – HunterCM

関連する問題