Golang Speed Limiting device

Source: Internet
Author: User
This is a creation in Article, where the information may have evolved or changed.

Speed limiter

Before seeing this two speed-limiting methods of golang concurrent programming, I think the way sleep waits is not particularly good, and it takes longer to wake up threads. and 1s within the request can only be evenly arrived, such as an instant to N, then only one can immediately return, the rest can only wait.

Amended
According to the instructions, whether it is sleep or Chan block, what happens is G and P separation, waiting for the next rotation, then proceed, so the likelihood can be almost the same. (This statement may not be accurate, not in depth)

The role of speed limiter is still more important, especially the use of more applications, if unrestricted, may be oom.

Simple idea: The default time interval is set to 1 seconds, simplifying the problem. If the limit () bool interface is called, if the number of runs in a second reaches a certain value, then it is blocked until the next 1 seconds are re-counted.

Code

Package Libimport ("Sync/atomic" "Time") type ratelimiter struct {limit UInt64 count UInt64 Ticker *time . Ticker Lockch Chan struct{}}func newratelimiter (limit UInt64) *ratelimiter {Ticker: = time. Newticker (time. Second) R: = &ratelimiter{limit:limit, count:0, Ticker:ticker, Lockch:make (chan struct{}),} go func () {for range ticker. C {if r.count > r.limit {select {case <-r.lockch:default                : R.resetcount ()}} if R.count > 0 { R.resetcount ()}}} () return R}func (R *ratelimiter) Limit () bool {R.addcou NT (1) if R.getcount () > R.limit {var s struct{} r.lockch <-s} return True}func (R *ratelim ITER) Addcount (interval UInt64) {atomic. AddUint64 (&r.count, Interval)}func (R *ratelimiter) GetCount () UInt64 {return atomic. LoadUint64 (&r.count)}func (R *ratelimiter) Resetcount () {Atomic. StoreUint64 (&r.count, 1)}

Test

package libimport (    "log"    "testing"    "time")func TestLimit(t *testing.T) {    limiter := NewRateLimiter(3)    start := time.Now()    for i := 0; i < 30; i++ {        if limiter.Limit() {            log.Printf("i is %d \n", i)        }    }    end := time.Now()    d := end.Sub(start)    log.Println("spends seconds: ", d.Seconds())}

Comparison

Compared to the first sleep implementation, the limiter is set to 3 times per second, Cycle 30 times, respectively:

2016/08/31 14:38:26 my limiter spends seconds:  9.00220346s2016/08/31 14:38:35 sleep limiter spends seconds:  9.762009934s

Here sleep limiter sleep more than two times, about 0.67s, minus this value equals 9.092009934.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.