示例代码请访问:github.com/wenjianzhan…
对象池
obj_pool.go
package obj_pool
import (
"errors"
"time"
)
type ReusableObj struct {
}
type ObjPool struct {
bufChan chan *ReusableObj
}
func NewObjPool(numOfObj int) *ObjPool {
objPool := ObjPool{}
objPool.bufChan = make(chan *ReusableObj, numOfObj)
for i := 0; i < numOfObj; i++ {
objPool.bufChan <- &ReusableObj{}
}
return &objPool
}
func (p *ObjPool) GetObj(timeout time.Duration) (*ReusableObj, error) {
select {
case ret := <-p.bufChan:
return ret, nil
case <-time.After(timeout):
return nil, errors.New("timeout")
}
}
func (p *ObjPool) ReleaseObj(obj *ReusableObj) ( error) {
select {
case p.bufChan <- obj:
return nil
default:
return errors.New("overflow")
}
}
obj_pool_test.go
package obj_pool
import (
"fmt"
"testing"
"time"
)
func TestObjPool(t *testing.T) {
pool := NewObjPool(10)
//if err := pool.ReleaseObj(&ReusableObj{}); err != nil {
// t.Error(err)
//}
for i := 0; i < 11; i++ {
if v, err := pool.GetObj(time.Second * 1); err != nil {
t.Error(err)
} else {
fmt.Printf("%T\n", v)
if err := pool.ReleaseObj(v); err != nil {
t.Error(err)
}
}
}
}
输出
=== RUN TestObjPool
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
*obj_pool.ReusableObj
--- PASS: TestObjPool (0.00s)
PASS
Process finished with exit code 0
其实我们只初始化了10个对象,但是我们使用了11次,并没有报错; 可以利用 buffer channel 可以缓存哪些难以创建可复用的对象;但也要进行性能测试,做出取舍
示例代码请访问:github.com/wenjianzhan…