In the daily development process, often encounter the use of resources to limit the frequency, for example: An interface allows only 300 calls per second, or a resource object only allow 300 per second, and so on, below is a simple speed limiter Java implementation, It can realize how many accesses are allowed to a resource in a certain amount of time (in milliseconds), and the implementation code is as follows:
Package Test_tmp;import Java.util.concurrent.concurrentlinkeddeque;import Java.util.concurrent.Semaphore; Public classspeedlimiter<t> {///two parameters maxusedlimited and timelimited are used to limit access speed, indicating that only resources resource are allowed to be used maxusedlimited times in timelimited milliseconds Public Speedlimiter(intMaxusedlimited,inttimelimited, T Resource) { This. maxusedlimited = maxusedlimited; This. timelimited = timelimited; This. resource = resource; M_semaphore =NewSemaphore (maxusedlimited * +/timelimited); } concurrentlinkeddeque<long> Statisticsinfo =NewConcurrentlinkeddeque<long> (); T resource =NULL;///The following two parameters are used to limit the speed of access Private intmaxusedlimited;Private inttimelimited;//statistics for a length of 1000 milliseconds, or 1 seconds //Use semaphores to restrict access to resources PrivateSemaphore M_semaphore =NULL; PublicSynchronized TConsume() {if(Statisticsinfo.size () >= maxusedlimited) {//already has a usage time record LongTI = Statisticsinfo.getlast ()-Statisticsinfo.getfirst ();if(Ti < timelimited) {//has been over-limited, that is, the number of times reached, but the time has not yet statistics_time, stating that the application is too fast, how much time to sleep how much timeSystem. out. println ("-------------resource access is restricted and is currently in the"+ Ti +"Access in milliseconds "+ statisticsinfo.size () +"Secondary Resources"); Safesleep (Timelimited-ti); } statisticsinfo.removefirst ();//The total number of times to, each time the oldest time to remove}//apply for re-recording time first Try{M_semaphore.acquire (); }Catch(Interruptedexception e) {E.printstacktrace (); } statisticsinfo.add (System.currenttimemillis ());returnResource } Public void Returnresource() {System. out. println ("-------------reclaim a resource, the current number of resources available:"+ m_semaphore.drainpermits ()); M_semaphore.release (); }Private void Safesleep(LongSleeptime) {Try{Thread.Sleep (sleeptime); }Catch(Interruptedexception e) {E.printstacktrace (); } }}
The following are examples of the use of the above-mentioned speed limiter:
The first is the code for the test thread:
Package test_tmp; Public class testspeedlimitedthread<T> extends Thread {speedlimiter<t> limiter =NULL; PublicTestspeedlimitedthread (speedlimiter<t> limiter) { This. limiter = limiter; } Public voidRun () {Longi =0; while(true) {T Tmpresource = Limiter.consume (); System.out.println ("Thread ID:"+ CurrentThread (). GetId () +" : ", (n+1) +": The resource has been acquired:"+ Tmpresource); i++;Try{Thread.Sleep (Ten); }Catch(Interruptedexception e) {//TODO auto-generated catch blockE.printstacktrace (); } limiter.returnresource (); } }}
The following is the code for the main test function:
PublicStaticvoidTestspeedlimiter () {StringResource= "MyResource"; Speedlimiter<String>Test= NewSpeedlimiter<String>( -, +, resource); Testspeedlimitedthread<String>TestThread1= NewTestspeedlimitedthread<String>(test); TestThread1.Start (); Testspeedlimitedthread<String>TestThread2= NewTestspeedlimitedthread<String>(test); TestThread2.Start (); Testspeedlimitedthread<String>TestThread3= NewTestspeedlimitedthread<String>(test); TestThread3.Start (); try {TestThread1.Join(); TestThread2.Join(); TestThread3.Join(); } catch (Interruptedexception e) {E.Printstacktrace (); } }
Java implementation of a simple speed limiter