如果你有一个东西, 你想别人触碰它的时候,不能同时触碰,需要按照你想要的每次多少人来触碰。

算了,不做比喻了,代码原理其实也简单,我们直接先看代码,我再做简单的解释(估计不用看解释也能懂):

package com.semaphore.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.ResponseBody;

import java.util.concurrent.Semaphore;

/**
* @Author : JCccc
* @CreateTime : 2018-11-27
* @Description :
* @Point: Keep a good mood
**/
@Controller
public class SemaphoreController {

//定义信号资源包的总数 只有2个
Semaphore semaphore=new Semaphore(2);


@GetMapping("/request")
@ResponseBody
public String Resquest(){
//设置这个接口可用的资源数
int availablePermits=semaphore.availablePermits();
if(availablePermits>0){
System.out.println("抢到资源");
}else{
System.out.println("资源已被占用,稍后再试");
return "Resource is busy!";
}
try {
//请求占用一个资源
semaphore.acquire(1);
System.out.println("资源正在被使用");
//放大资源占用时间,便于观察
Thread.sleep(30000);
} catch (InterruptedException e) {
e.printStackTrace();
}finally{
semaphore.release(1);//释放一个资源
System.out.println("-----------释放资源包----------");
}
return "Success";
}

}

运行的结果图(以极快的手速一起调用接口进行访问):

 

Springboot 线程同步之Semaphore 的简单使用_Semaphore 

 

简单解析:

我在代码里面设置的可用的资源包是:

//定义资源包的总数 只有2个
Semaphore semaphore=new Semaphore(2);
//设置这个接口可用的资源数
int availablePermits=semaphore.availablePermits();

然后这个整体的运行流程就是这样:

一个请求调用接口,那么就会先去判断资源包还有没有?

如果有,那就抢;抢到了,就开始使用!且,此刻可用的总资源包就-1  :

//请求占用一个资源
semaphore.acquire(1);

如果没有,那就直接返回了提示,就是说资源紧张~

然后在抢到资源包开始使用的时候,我们可以看到控制台输出了一下,资源正在被使用,顾名思义(就是说有人在使用咯,当然你可以扩展,作为日志跟踪,我之前的博客有介绍怎么获取请求者的IP地址也有怎么生成日志等等)

然后在使用完毕的时候,就释放资源包,

//释放一个资源
semaphore.release(1);

那么如果刚好这时候有请求过来了,那就可以申请使用资源包了。

结合我的运行结果:

我一共设置2个可用资源包,然后同时跑起来5个请求, 然后就看到了前面2个请求都抢到了资源,后面的都显示资源紧张。 

嗯,简单的使用介绍就这样了。 当然如果感兴趣这个玩意,推荐去再了解下限流 漏桶算法和令牌桶算法。