线程(十四)线程同步技术Semaphore

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u014252478/article/details/83828191

理解:

Semaphore通常用于限制可以访问某些资源(物理或逻辑的)的线程数目,我们可以自己设定最大访问量。它有两个很常用的方法是acquire()release(),分别是获得许可和释放许可。 

借用武哥的理解:

Semaphore相当于一个厕所,我在造的时候可以想造几个坑就造几个坑,假如现在我就造了3个坑,现在有10个人想要来上厕所,那么每次就只能3个人上,谁最先抢到谁就进去,出来了一个人后,第4个人才能进去,这个就限制了上厕所的人数了,就这个道理。每个人上厕所之前都先acquire()一下,如果有坑,就可以进入,没有就被阻塞,在外面等;上完厕所后,会release()一下,释放一个坑出来,以保证下一个人acquire()的时候有坑。
 

实例1:

public class SemaphoreTest {

    public static void main(String[] args) {

        ExecutorService service = Executors.newCachedThreadPool();//使用并发库,创建缓存的线程池
        final Semaphore sp = new Semaphore(3);//创建一个Semaphore信号量,并设置最大并发数为3

        //availablePermits() //用来获取当前可用的访问次数
        System.out.println("初始化:当前有" + (3 - sp.availablePermits() + "个并发"));

        //创建10个任务,上面的缓存线程池就会创建10个对应的线程去执行
        for (int index = 0; index < 10; index++) {
            final int NO = index;  //记录第几个任务
            Runnable run = new Runnable() {  //具体任务
                public void run() {  
                    try {                          
                        sp.acquire();  // 获取许可 
                        System.out.println(Thread.currentThread().getName() 
                            + "获取许可" + "("+NO+")," + "剩余:" + sp.availablePermits());  
                        Thread.sleep(1000);  
                        // 访问完后记得释放 ,否则在控制台只能打印3条记录,之后线程一直阻塞
                        sp.release();  //释放许可
                        System.out.println(Thread.currentThread().getName() 
                            + "释放许可" + "("+NO+")," + "剩余:" + sp.availablePermits());  
                    } catch (InterruptedException e) {  
                    }  
                }  
            };  
            service.execute(run);  //执行任务
        }         
        service.shutdown(); //关闭线程池
    }
}

猜你喜欢

转载自blog.csdn.net/u014252478/article/details/83828191