📘 Article Content:
Java’s memory management model is built around the Java Virtual Machine (JVM) heap, which is the area where all class instances and arrays are allocated. To improve garbage collection (GC) performance, the JVM divides the heap into multiple generations based on object lifespan. Let’s break down the key parts of the heap and understand how they work.
🔹 JVM Heap Structure: The Generational Model
1. Young Generation (Young Gen)
The Young Generation is where all new objects are created. It's optimized for fast allocation and collection, as most objects die young.
Components:
- Eden Space:
- New objects are first allocated here. When Eden becomes full, a Minor GC is triggered.
- Survivor Spaces (S0 and S1):
- There are two Survivor spaces (also called "From" and "To"). During a Minor GC, live objects from Eden are copied into one of these. With each GC cycle, objects may be copied back and forth between these two until they're eventually promoted to the Old Generation.
2. Old Generation (Tenured Gen)
The Old Generation stores long-lived objects — those that have survived several Minor GCs. It's typically larger than the Young Gen and collected less frequently. When it becomes full, a Major GC (or Full GC) occurs, which is more time-consuming.
3. Permanent Generation (PermGen) [Deprecated]
Used in Java versions before 8, PermGen stored metadata like class definitions, method info, and static variables. Its fixed size often led to OutOfMemoryError
s, prompting its deprecation.
4. Metaspace (Java 8+)
Introduced in Java 8, Metaspace replaced PermGen. It serves the same role of storing class metadata, but unlike PermGen, Metaspace:
- Is not part of the heap
- Grows dynamically based on available native memory
This change greatly reduced memory-related issues related to class loading.
🔹 Types of Garbage Collection
Minor GC
- Targets Young Generation only
- Happens frequently
- Fast and efficient, as most short-lived objects can be discarded quickly
Major GC
- Targets the Old Generation
- Slower than Minor GC
- Can cause application pauses due to its extensive scope
Full GC
- Sweeps both Young and Old Generations, and sometimes Metaspace
- Most expensive in terms of time and resources
- Should be minimized in high-throughput applications
🔹 Lifecycle Example of Objects in the JVM Heap
text
1. Object is created → goes to Eden
2. Eden fills up → Minor GC runs
3. Live objects → moved to Survivor S0
4. Survives several GCs → promoted to Old Gen
5. Old Gen fills → Major/Full GC reclaims space
🔹 Tuning the JVM Heap
Fine-tuning the heap and GC behavior can significantly improve performance.
Common JVM Options:
bash
-Xms<size> # Initial heap size
-Xmx<size> # Maximum heap size
-XX:NewSize=<size> # Initial size of Young Generation
-XX:MaxNewSize=<size> # Maximum size of Young Generation
-XX:MetaspaceSize=<size> # Initial size of Metaspace (Java 8+)
-XX:MaxMetaspaceSize=<size> # Maximum size of Metaspace
Example:
bash
java -Xms512m -Xmx2g -XX:NewSize=256m -XX:MaxMetaspaceSize=512m -jar your-app.jar
🔹 Summary
GenerationPurposeKey GC TypeYoung GenHolds new, short-lived objectsMinor GCOld GenStores long-lived or promoted objectsMajor/Full GCMetaspaceStores class metadata (Java 8+)Part of Full GCPermGenDeprecated metadata storage (Java < 8)N/A
Understanding how JVM memory is structured helps in optimizing garbage collection and improving the performance and scalability of Java applications.