一、令牌桶算法和漏桶算法
1、漏桶算法,有一个固定大小的桶,桶中的流量按照固定的速率流出,此时若有流量流入桶中,如果流入的速率比流出的速率大,则可能导致超过桶大小的流量溢出。
2、令牌算法,有一个固定大小的桶,按照一定的速率往桶中放入令牌,如果令牌超过桶大小则会溢出,此时若有流量需要发送,则先到令牌桶取发送的数目(如果数目不足则等待一段时间再取),令牌桶的数目相应的减少。
区别:漏桶算法只允许按照一定的速率发送,而令牌桶根据令牌数目来发送,最大可允许发送桶大小的流量。
二、令牌桶测试(golang)
package main
import (
"fmt"
"time"
)
//桶容量
var capacity int64 = 256 * 1024 * 1024
//令牌放入的速度
var rate int64 = 128 * 1024 * 1024
//当前令牌数量
var tokens int64 = 0
var timestamp time.Time = time.Now()
func min(va, vb int64) int64 {
if va <= vb {
return va
}
return vb
}
func grant(packetsize int64) bool {
if packetsize > capacity || packetsize < 1 {
return false
}
now := time.Now()
//获取令牌桶的令牌数量---如果生成的令牌数量多于桶容量,则溢出
tokens = min(capacity, tokens+(now.Unix()-timestamp.Unix())*rate)
timestamp = now
if tokens < packetsize {
return false
} else {
tokens -= packetsize
return true
}
}
func main() {
if ret := grant(1024 * 1024 * 128); ret {
fmt.Println("trans packet at first")
return
}
select {
case <-time.After(time.Second):
break
}
if ret := grant(1024 * 1024 * 128); ret {
fmt.Println("trans packet at second")
return
}
fmt.Println("No trans")
}