Re: [go-nuts] when to use Sync pool

2017-10-09 Thread Val
Good point, thank you Bryan.

Also note that assigning a func value to p.New seems standard for the use case 
"if nil, then create one" (I don't know the perf implications).

Cheers
Val

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: [go-nuts] when to use Sync pool

2017-10-09 Thread 'Bryan Mills' via golang-nuts
On Friday, October 6, 2017 at 5:32:06 PM UTC-4, Ian Lance Taylor wrote:
>
> On Fri, Oct 6, 2017 at 1:23 PM, XXX ZZZ  
> wrote: 
> > 
> > So we are making a platform where we have to use a TON of short lived 
> > structs, in order to optimize this we intend to use sync pool, however 
> on 
> > our benchmark tests I have found that it only seems to improve 
> performance 
> > when the struct is big enough, for smaller structs ie: (4-5 string 
> values) 
> > it seems to be considerably slower, yet I see many packages (such as 
> > fasthttp) using sync pool for basically everything. Is there anything I 
> am 
> > missing? Any recommendations of when to use sync pool? 
>
> Be careful in your benchmarks.  Make sure that the values are really 
> being allocated, and not simply being stored on the stack by the 
> compiler.  Check how often the GC is running; allocation that does not 
> trigger a GC is always going to be faster. 
>
> Use sync.Pool when you have code that uses an unpredictable number of 
> objects, where the allocation cost of the objects is noticeable 
> compared to the cost of the rest of the code (either because the 
> objects are large or because the rest of the code is fast), where you 
> want to scale the allocation require based on the use of the package. 
> Don't use sync.Pool if the number of objects is predictable: use a 
> free list.  Don't use it for basically everything; it won't actually 
> save you any time.  Use it for areas where the memory needs change 
> unpredictably during the course of the program.


One of the interesting things I've noticed with sync.Pool is that the cost 
of boxing an unboxing the `interface{}` argument can sometimes swamp out 
the savings from pooling the objects: the interaction with escape analysis 
is particularly subtle.

You may be tempted to type-assert the return value from `Get` immediately 
to keep the code clean, like this:

```
p, _ := pool.Get().(*someType)
if p == nil {
p = new(someType)
}
…
pool.Put(p)
```

If your benchmarks turn out anything like mine did, you'll instead want 
something like:

```
var (
p *someType
i = pool.Get()
)
if i == nil {
p = new(someType)
i = p
} else {
p = i.(*someType)
}
…
pool.Put(i)
```

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: [go-nuts] when to use Sync pool

2017-10-06 Thread Ian Lance Taylor
On Fri, Oct 6, 2017 at 1:23 PM, XXX ZZZ  wrote:
>
> So we are making a platform where we have to use a TON of short lived
> structs, in order to optimize this we intend to use sync pool, however on
> our benchmark tests I have found that it only seems to improve performance
> when the struct is big enough, for smaller structs ie: (4-5 string values)
> it seems to be considerably slower, yet I see many packages (such as
> fasthttp) using sync pool for basically everything. Is there anything I am
> missing? Any recommendations of when to use sync pool?

Be careful in your benchmarks.  Make sure that the values are really
being allocated, and not simply being stored on the stack by the
compiler.  Check how often the GC is running; allocation that does not
trigger a GC is always going to be faster.

Use sync.Pool when you have code that uses an unpredictable number of
objects, where the allocation cost of the objects is noticeable
compared to the cost of the rest of the code (either because the
objects are large or because the rest of the code is fast), where you
want to scale the allocation require based on the use of the package.
Don't use sync.Pool if the number of objects is predictable: use a
free list.  Don't use it for basically everything; it won't actually
save you any time.  Use it for areas where the memory needs change
unpredictably during the course of the program.

Ian

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.