8 ms·
How the Go GC does comparing with the JVM one ?
by siscia 11y ago
How the Go GC does comparing with the JVM one ?
- omginternets 11y agoIn terms of what? Latency? I think Go is down to something like 10ms, and from what I understand, pressure on the GC can be relieved by using things such as `sync.Pool`.
- vardump 11y agoJVM's gc is most likely significantly better. On the other hand golang's gc needs to collect less objects, in some cases orders of magnitude less. If you compare a slice of structs with 1000 elements, it'll be one object (and allocation) in golang. Equivalent array in JVM requires the array itself + 1000 Objects, 1001 allocations. In this case, golang has lot less object graph to gc. Of course slice of 1000 interfaces or pointers faces the same 1001 issue in golang as well. You could emulate same gc load cost in JVM at cost of runtime performance by storing the objects in a byte array and [de]serialize as needed, but that's neither idiomatic or acceptable solution most of the time.
- pjmlp 11y agoHopefully Java will get value types around version 10, but that is still quite far away. In the meantime, Azul and IBM JVMs JITs are able to optimize "value types" if the classes follow certain patterns or with some annotation help.
- aardvark179 11y agoYeah, and they can collect the unreachable objects in the array when no references exist to the array itself. From the QCon talk linked to in the slides it sounds like the Go GC is benefiting from the reduced number of objects being allocated and the fact that those objects can never move. Makes things a lot simpler if you can get away with it, but I can imagine a reference into an array, and the inability to move objects could combine in bad ways if you're unlucky.
- leaveyou 11y agoCould you explain what essential things JVM does better than Go at this point ? Does it stop the world less ? Or does it do more things in parallel ? Thanks
- loganekz 11y agoAlthough Go's GC is tunable to some extent, the open source HotSpot JVM are already has multiple GC implementations that you can choose based on your use case and further tune. There is also work being done in the OpenJDK project for a GC that can collect > 100GB heaps in < 10ms [1]. There are also alternative proprietary implementations available today that already have no stop the world collections [2] [1] http://openjdk.java.net/jeps/189 http://openjdk.java.net/jeps/189 [2] https://www.azul.com/products/zing/ https://www.azul.com/products/zing/
- leaveyou 11y agoFrom this "work being done in the OpenJDK project for a GC that can collect > 100GB heaps in < 10ms" I deduce that Go 1.6 is not that bad at all and 1.7 or 1.8 could even beat that easily. https://talks.golang.org/2016/state-of-go.slide#37 https://talks.golang.org/2016/state-of-go.slide#37 https://github.com/golang/proposal/blob/master/design/12800-sweep-free-alloc.md https://github.com/golang/proposal/blob/master/design/12800-...
- pcwalton 11y agoLatency isn't the only concern; you also have to look at throughput. The JVM's GC has been carefully tuned to strike a balance here. In particular, Go's GC is not yet generational from the talks I've seen, which is a large throughput loss compared to the GC of the JVM.
- geodel 11y agoIf it is carefully tuned why it needs such a big GC tuning guide and 100s of JVM flags to tune runtime. Any Java product of consequence comes with custom GC settings meaning they do not find default ones suitable. https://docs.oracle.com/javase/8/docs/technotes/guides/vm/gctuning/ https://docs.oracle.com/javase/8/docs/technotes/guides/vm/gc...
- voidlogic 11y agoGo is also better about allocating on the stack (vs heap) and provides a very solid pool implementation (sync.Pool). Both of these can dramatically reduce GC pressure too.
- kasey_junk 11y agoThe golang object pool is a bit of a problem (compared to the JVM alternatives) due to lack of generics. You tend to need to do object pooling when you have tight performance requirements which is at odds with the type manipulation you have to do with the sync.Pool. So the golang pool is good for the case where you have GC heavy but non-latency sensitive operations, but not the more general performance sensitive problems.
- voidlogic 11y agoHave you benched "myPool.Get()" vs "myPool.Get().(*myStruct)" ? I don't think the "type manipulation" is the problem you think it is.
- pcwalton 11y agoAt the x86 level, myPool.Get(Index) is going to be at least as expensive as cmp/jae/mov (3 cycles), and myPool.Get().(myStruct) is going to be at least as expensive as cmp/jae/cmp/jne/mov (5 cycles). So unless you have some way of hiding the latency, the type check is 67% slower by cycle count. The experience of every JIT developer is that dynamic type checks do matter a lot in hot paths.
- voidlogic 11y agoThis is a small fixed cost as compared to the cost of not using the pool. I wasn't suggesting the operation is free.
- kasey_junk 11y agoBut not using a pool is not the alternative we are talking about. Rather its hand rolling your own every time. Something the JVM doesn't require.