为了了解sync.Pool,我为它编写了两种不同的新方法:
基准令我吃惊
1 alloc
请解释为什么1和3之间有这么大的差异,因为两者都分配内存?为什么第一次分配?
package main
import (
"bytes"
"sync"
)
func main() {}
type MyBuffer struct {
pool sync.Pool
}
func New() *MyBuffer {
return &MyBuffer{pool: sync.Pool{
New: func() any {
buf := make([]int, 0, 128)
return &buf
},
}}
}
func New2() *MyBuffer {
return &MyBuffer{pool: sync.Pool{
New: func() any {
buf := make([]int, 0, 128)
return buf
},
}}
}
func Fill[S ~[]E, E any](buf *S) {
var some E
for i := 0; i < cap(*buf); i++ {
*buf = append(*buf, some)
}
}
func BenchmarkAlloc(b *testing.B) {
b.RunParallel(func(p *testing.PB) {
for p.Next() {
// Get buf
buf := make([]int, 0, 128)
// fill
Fill(&buf)
// Reset
buf = buf[:0]
}
})
}
func BenchmarkPoolPtr(b *testing.B) {
mb := New()
b.RunParallel(func(p *testing.PB) {
for p.Next() {
// Get buf
buf, _ := mb.pool.Get().(*[]int)
// fill
Fill(buf)
// reset
*buf = (*buf)[:0]
// put
mb.pool.Put(buf)
}
})
}
func BenchmarkPoolNoPtr(b *testing.B) {
mb := New2()
b.RunParallel(func(p *testing.PB) {
for p.Next() {
// Get buf
buf, _ := mb.pool.Get().([]int)
// fill
Fill(&buf)
// reset
buf = buf[:0]
// put
mb.pool.Put(&buf)
}
})
}发布于 2022-10-23 22:26:59
我认为在第一种情况下,分配是对您的切片的参考。在第三种情况下,分配是完整的部分。当您查看分配的大小时,它是32 B/op和1024 B/op,所以分配是对您的片的引用,当变量是指针时,这是不需要的。
https://stackoverflow.com/questions/74169639
复制相似问题