• Tags
  •         
  • www.breakyizhan.com
  •    

    Java中的信号量Semaphore是我们上一节讲到的。

    public class Semaphore
    extends Object
    implements Serializable

    从概念上讲,信号量保持一组许可。如果需要,每个acquire()都会阻止,直到有许可证可用,然后接受它。每个版本()都会添加许可证,可能会释放阻塞收单器。但是,没有使用实际的许可对象; 信号量只保留可用数量并相应地采取行动。

    Java中的Java.util.concurrent.Semaphore类的方法

    1. void acquire():此方法获取许可,如果有,并立即返回,将可用许可数减少一。如果当前线程在等待许可时被中断,则抛出InterruptedException。
      句法 : 
      public void acquire()抛出InterruptedException
      参数: 
      NA
      返回:
      NA
      抛出:
      InterruptedException  - 如果当前线程被中断
      
    2. void acquire(int permit):此方法获取给定数量的许可(如果可用),并立即返回,减少给定数量的可用许可数。如果当前线程在等待许可时被中断,则InterruptedException为抛出。
      句法 : 
      public void acquire(int permits)抛出InterruptedException
      参数: 
      permits - 获得许可证的数量
      返回:
      NA
      抛出:
      InterruptedException  - 如果当前线程被中断
      IllegalArgumentException  - 如果permit是否定的
      
    3. void acquireUninterruptibly():此方法获取许可,如果有可用并立即返回,则将可用许可数减少一个。如果当前线程在等待许可时被中断,则它将继续等待,
      句法 : 
      public void acquireUninterruptibly()
      参数: 
      NA
      返回:
      NA
      
    4. void acquireUninterruptibly(int permit):此方法给定许可数,如果可用,则立即返回,减少给定数量的可用许可数。如果当前线程在等待许可时被中断,那么它将继续等待,
      句法 : 
      public void acquireUninterruptibly(int permit)
      参数: 
      permit - 获得许可证的数量
      返回:
      NA
      抛出:
      IllegalArgumentException  - 如果permit是否定的
      
    5. boolean tryAcquire():此方法获取许可证(如果有)并立即返回,值为true,将可用许可证数量减少一个。如果没有可用许可证,则此方法将立即返回值false。
      句法 : 
      public boolean tryAcquire()
      参数: 
      NA
      返回:
      如果获得许可,则为true,否则为false
      
    6. boolean tryAcquire(int permits):此方法获取给定数量的许可证(如果可用),并立即返回,值为true,减少给定数量的可用许可证数量。如果许可证不足,则此方法将立即返回值false。
      句法 : 
      public boolean tryAcquire(int permit)
      参数: 
      许可证 - 获得许可证的数量
      返回:
      如果获得许可证则为true,否则为false
      抛出:
      IllegalArgumentException  - 如果permit是否定的
      
    7. boolean tryAcquire(long timeout,TimeUnit unit):此方法获取许可,如果有,并立即返回,值为true,将可用许可数减1。如果指定的等待时间过去,则返回值false。如果时间小于或等于零,则该方法将不会等待。
      句法 : 
      public boolean tryAcquire(long timeout,TimeUnit unit)
           抛出InterruptedException
      参数: 
      timeout - 等待许可的最长时间
      unit  - 超时参数的时间单位
      返回:
      如果获得许可证,则为真 
      如果在获得许可之前等待时间已过,则为假
      抛出:
      InterruptedException  - 如果当前线程被中断
      
    8. boolean tryAcquire(int permit,long timeout,TimeUnit unit):此方法获取给定数量的许可,如果它们可用并立即返回,值为true,则减少给定数量的可用许可数。如果指定的等待时间过去,则返回值false。如果时间小于或等于零,则该方法将不会等待。任何允许分配给该线程的许可将被分配给试图获取许可的其他线程。
      句法 : 
      public boolean tryAcquire(int permit,long timeout,TimeUnit unit) 
      抛出InterruptedException
      参数: 
      permit - 获得许可证的数量
      timeout - 等待许可的最长时间
      unit  - 超时参数的时间单位
      返回:
      如果获得了所有许可,则为真 
      如果等待时间过去之前是假的 
      获得许可证
      抛出:
      InterruptedException  - 如果当前线程被中断
      IllegalArgumentException  - 如果permit是否定的
      
    9. void release():此方法释放许可证,将可用许可证数量增加一个。如果任何线程试图获得许可证,则选择一个并获得刚刚发布的许可证。
      句法 : 
      public void release()
      参数: 
      NA
      返回:
      NA
      
    10. void release(int permit :此方法释放给定数量的许可,增加该数量的可用许可数。如果任何线程试图获得许可,则选择一个并给出刚刚发布的许可。如果可用许可证的数量满足该线程的请求,则该线程被(重新)启用以进行线程调度; 否则线程将等待,直到有足够的许可证可用。
      句法 : 
      public void release(int permit)
      参数: 
      permit - 释放许可证的数量
      返回:
      NA
      抛出: 
      IllegalArgumentException  - 如果permit是否定的
      
    11. int availablePermits():此方法返回此信号量中可用的当前许可数。此方法通常用于调试和测试目的。
      句法 : 
      public int availablePermits()
      参数: 
      NA
      返回:
      此信号量中可用的许可数量
      
    12. int drainPermits():此方法获取并返回所有可立即使用的许可。
      句法 : 
      public int drainPermits()
      参数: 
      NA
      返回:
      获得的许可证数量
      
    13. void reducePermits(int reduction):此方法通过指示的减少量缩减可用许可证的数量。此方法在使用信号量跟踪变为不可用的资源的子类中非常有用。该方法与获取的不同之处在于它不会阻止等待许可变得可用。
      句法 : 
      protected void reducePermits(int reduction)
      参数: 
      减少 - 要删除的许可数量
      返回:
      NA
      抛出:
      IllegalArgumentException  - 如果减少为负数
      
    14. boolean isFair():如果此信号量的公平性设置为true,则此方法返回true。
      句法 : 
      public boolean isFair()
      参数: 
      NA
      返回:
      如果此信号量具有公平性,则为true
      
    15. final boolean hasQueuedThreads():此方法查询是否有任何线程正在等待获取。请注意,由于取消可能随时发生,因此真正的返回并不能保证任何其他线程都能获得。该方法主要用于监视系统状态。
      句法 : 
      public final boolean hasQueuedThreads()
      参数: 
      NA
      返回:
      如果可能有其他线程等待获取锁定,则为true
      
    16. final int getQueueLength():此方法返回等待获取的线程数的估计值。该值只是一个估计值,因为当此方法遍历内部数据结构时,线程数可能会动态更改。此方法设计用于监视系统状态,而不是用于同步控制。
      句法 : 
      public final int getQueueLength()
      参数: 
      NA
      返回:
      等待此锁定的估计线程数
      
    17. Collection getQueuedThreads():此方法返回包含可能正在等待获取的线程的集合。因为实际的线程集可能在构造此结果时动态更改,所以返回的集合仅是尽力而为的估计。返回集合的元素没有特定的顺序。
      语法: 
      protected CollectiongetQueuedThreads()
       参数:
      NA
      返回:
      线程集合
      
    18. String toString():此方法返回标识此信号量及其状态的字符串。括号中的状态包括字符串“Permits =”,后跟许可数。
      句法 : 
      public String toString()
      参数: 
      NA
      返回:
      标识此信号量的字符串及其状态
      覆盖: 
      类Object中的 toString
      

    解释Java.util.concurrent.Semaphore类方法的示例

    请注意,输出始终不相同。

    // Java program to demonstrate
    // methods of Semaphore class
    import java.util.concurrent.*;
      
    class MyThread extends Thread
    {
        Semaphore sem;
        String threadName;
        public MyThread(Semaphore sem, String threadName)
        {
            super(threadName);
            this.sem = sem;
            this.threadName = threadName;
        }
     
        @Override
        public void run() {
             
                // First, get a permit.
                System.out.println(threadName + " is waiting for a permit.");
              
                   try {
                     // acquire method
                    sem.acquire();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                 
                   System.out.println(threadName + " gets a permit");
             
                // Now, critical section
                // other waiting threads will wait, until this
                   // thread release the lock
                for(int i=0; i < 2; i++)
                {
                     // hasQueuedThreads() methods
                     boolean b = sem.hasQueuedThreads();
                     if(b)
                         // getQueuedLength() methods
                         System.out.println("Length of Queue : " + sem.getQueueLength())    ;
             
                     // Now, allowing a context switch -- if possible.
                     try {
                        Thread.sleep(10);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
       
             
                // Release the permit.
                System.out.println(threadName + " releases the permit.");
                    
                // release() method
                sem.release();
            }
    }
     
    // Driver class
    public class SemaphoreDemo
    {
        public static void main(String args[]) throws InterruptedException
        {
            // creating a Semaphore object
            // with number of permits 3 and fairness true
            Semaphore sem = new Semaphore(3, true);
            
            //isFair() method
            System.out.println("is Fairness enabled : " + sem.isFair());
            
            // Main thread try to acquire 2 permits
            // tryAcquire(int permits) method
            sem.tryAcquire(2);
            
            // availablePermits() method
            System.out.println("Available permits : " + sem.availablePermits());
            
            //drainPermits() method
            System.out.println("number of permits drain by Main thread : "
                                          + sem.drainPermits());
            
            // permit released by Main thread
            sem.release(1);
            
            // creating two threads with name A and B
            MyThread mt1 = new MyThread(sem, "A");
            MyThread mt2 = new MyThread(sem, "B");
             
            
            // starting threads A
            mt1.start();
            
            // starting threads B
            mt2.start();
            
            // toString method
            System.out.println(sem.toString());
            
             
            // waiting for threads A and B
            mt1.join();
            mt2.join();
        }
    }
    

    输出:

    is Fairness enabled : true
    Available permits : 1
    number of permits drain by Main thread : 1
    java.util.concurrent.Semaphore@7852e922[Permits = 1]
    B is waiting for a permit.
    B gets a permit
    A is waiting for a permit.
    Length of Queue : 1
    B releases the permit.
    A gets a permit
    A releases the permit.
     
    转载请保留页面地址:https://www.breakyizhan.com/java/4971.html