1

私は、セマフォを4のカウントと6つのスレッドで初期化する単純なセマフォプログラムに取り組んでいます。 実行メソッドの中で、私はセマフォー・ロックを取得しています。各スレッドの完了後、ロックを解除しています。ファーストインファーストパラメータに先行しないセマフォのフェアネスパラメータ

は、ここに私のコードです:

import java.util.concurrent.Semaphore; 

public class SemaphoreTest { 

    static Semaphore semaphore = new Semaphore(4, true); 

    static class MyThread extends Thread{ 

     String name = ""; 

     public MyThread(String name){ 
      this.name = name; 

     } 

     public void run(){ 

      System.out.println(name+" going to acquire lock..."); 
      System.out.println("Available Permits = "+semaphore.availablePermits()); 

      try { 
       semaphore.acquire(); 
       System.out.println(name+" got permit."); 

       try{ 
        for(int i=1;i<=1;i++){ 
         System.out.println(name+" is performing operation "+i+". Available Semaphore permits are : "+semaphore.availablePermits()); 
         Thread.sleep(1000); 
        } 

       }finally{ 
        System.out.println(name+" Releasing lock..."); 
        semaphore.release(); 
        System.out.println("Available permits after releasing "+"name"+" = "+semaphore.availablePermits()); 
       } 
      } catch (InterruptedException e) { 
       // TODO Auto-generated catch block 
       e.printStackTrace(); 
      } 


     } 
    } 

    public static void main(String[] args){ 
     Thread t1 = new MyThread("A"); 
     t1.start(); 

     Thread t2 = new MyThread("B"); 
     t2.start(); 

     Thread t3 = new MyThread("C"); 
     t3.start(); 

     Thread t4 = new MyThread("D"); 
     t4.start(); 

     Thread t5 = new MyThread("E"); 
     t5.start(); 

     Thread t6 = new MyThread("F"); 
     t6.start(); 
    } 

} 

そして、ここでの結果です:Javaドキュメントのように今

A going to acquire lock... 
Available Permits = 4 
C going to acquire lock... 
A got permit. 
A is performing operation 1. Available Semaphore permits are : 3 
B going to acquire lock... 
Available Permits = 3 
B got permit. 
F going to acquire lock... 
E going to acquire lock... 
Available Permits = 2 
Available Permits = 3 
D going to acquire lock... 
Available Permits = 0 
C got permit. 
C is performing operation 1. Available Semaphore permits are : 0 
E got permit. 
E is performing operation 1. Available Semaphore permits are : 0 
Available Permits = 2 
B is performing operation 1. Available Semaphore permits are : 2 
A Releasing lock... 
E Releasing lock... 
Available permits after releasing name = 2 
D got permit. 
D is performing operation 1. Available Semaphore permits are : 1 
B Releasing lock... 
C Releasing lock... 
Available permits after releasing name = 1 
F got permit. 
F is performing operation 1. Available Semaphore permits are : 2 
Available permits after releasing name = 2 
Available permits after releasing name = 2 
D Releasing lock... 
F Releasing lock... 
Available permits after releasing name = 3 
Available permits after releasing name = 4 

java.util.concurrent.Semaphore。セマフォー(int permit、boolean fair)

Cr指定された数の許可と指定された公平設定でセマフォを生成します。

パラメータ:
permits利用可能な初期許可数。この値は負の値になることがあります。この場合、取得が許可される前にリリースが行われなければなりません。
他の真fairこのセマフォは、第一に保証される場合は許可証の最初のアウト付与競合の下で、偽

をコンストラクタセマフォ(int型の許可、ブール公正)、先入れ先出し保証。しかし、このプログラムの結果として、それは同じではありません。 > B - - > C - > E

、以下のようにロックが解除され

A:

A - > E - >を次のように ロックが後天れますB - > C

期待どおりですか?それとも、私は行方不明の何かがありますか?

答えて

2

許可が解放される順序は、単にrunメソッドで費やされた時間の結果であり、公平性とは何の関係もありません。

ここでFIFOとは、2つのスレッドがsemaphore.acquire()を呼び出し、使用可能でない場合、最初に呼び出したスレッドが、使用可能になったときに最初に許可を受け取ることを意味します。

あなたの例では、A、B、C、Eはacquireを最初に呼び出し、許可が利用可能になるのを待たなければならないため許可を得ます。それから、DはFの前にacquireを呼び出して、最初に利用可能な許可を得ているようです。

0

ここでスレッドタイミングについて誤解があります。スレッドがメッセージを出力するとすぐにロックを取得すると仮定しますが、実際にはその間にスレッドをホールドしない理由はありません。

C: System.out.println(...); 
C: thread gets put on hold 
A: System.out.println(...); 
A: aquires lock 
B: System.out.println(...); 
B: aquires lock 
C: resumes 
C: aquires lock 
関連する問題