← All articles
Backend1 min read

Garbage Collection Tuning Basics

Most apps never need GC tuning, but when latency spikes appear, knowing which collector you run and how to read its logs is essential.

S

Swapnika Voora

Author

The JVM reclaims memory automatically, but the collector you choose trades throughput against pause time. Understanding that trade-off is the first step before touching a single flag.

Pick the right collector

G1 is the default and balances pauses with throughput. For large heaps that need very low pauses, ZGC is worth a look.

jvm-flags.sh
# G1 with a pause-time goal
java -XX:+UseG1GC -XX:MaxGCPauseMillis=100 -Xmx4g -jar app.jar
 
# ZGC for very large heaps and sub-millisecond pauses
java -XX:+UseZGC -Xmx16g -jar app.jar

Read the logs before tuning

Enable unified GC logging and measure — never tune blind.

gc-log.sh
java -Xlog:gc*:file=gc.log:time,uptime -jar app.jar

Takeaways

  • Set -Xms equal to -Xmx in containers to avoid heap resizing pauses.
  • Measure allocation rate before assuming the collector is the problem.
  • Most "GC problems" are actually memory leaks or oversized caches.

Reducing allocation — reusing buffers, avoiding needless boxing — usually beats any collector flag you can set.

#java#jvm#performance

More in Backend