What is Garbage Collection?
Garbage Collection (GC) is a mechanism provided by programming languages like Java to automatically free memory that is no longer referenced by any part of the program. This helps prevent memory leaks, optimizes performance, and reduces the burden on developers to manually manage memory allocation and deallocation.
In Java, the JVM (Java Virtual Machine) automatically runs the garbage collector at appropriate times, freeing up memory occupied by objects that are no longer reachable.
How Garbage Collection Works?
Java's memory is divided into different regions:
- Heap Memory: Where all objects are stored
- Young Generation: Newly created objects (Eden space + Survivor spaces)
- Old Generation (Tenured): Objects that have survived multiple GC cycles
- Metaspace (PermGen in older Java): Stores class metadata
GC algorithms identify unreachable objects by traversing object graphs starting from "GC Roots" (local variables, active threads, static variables, etc.).
Types of Garbage Collectors in Java
Serial GC
Uses a single thread for GC. Best for single-threaded applications and small heaps.
Parallel GC
Uses multiple threads for GC. Suitable for multi-threaded applications. Default until Java 8.
CMS GC
Concurrent Mark Sweep - minimizes pause times. Deprecated in newer Java versions.
G1 GC
Garbage First - balances throughput and pause times. Default from Java 9 onwards.
ZGC
Scalable low-latency GC. Handles large heaps (terabytes) with minimal pauses.
Shenandoah GC
Low-pause time GC. Performs compaction concurrently with application threads.
Objectives of Garbage Collection
1. Automatically manage memory allocation and deallocation
📌 Example: When objects go out of scope, GC frees memory without manual intervention, eliminating the need for explicit delete/free operations.2. Prevent memory leaks and dangling references
📌 Example: Removing unreferenced objects ensures the application does not consume unnecessary memory over time, preventing OutOfMemoryError.3. Improve application performance and stability
📌 Example: Consistent memory usage reduces crashes, improves response times, and provides predictable performance.4. Simplify development by removing manual memory management
📌 Example: Developers can focus on business logic rather than tracking every object's lifecycle.Advantages of Garbage Collection
1. No need for manual memory management
📌 Programmers can focus on logic without worrying about freeing memory, reducing development time.2. Reduces programmer errors related to memory
📌 Eliminates common errors like dangling pointers, double-free, and memory leaks.3. Helps maintain consistent application performance
📌 Automatic memory cleanup prevents sudden memory spikes and OutOfMemoryErrors.4. Platform-independent memory management
📌 Developers don't need to write platform-specific memory code; JVM handles it uniformly.Limitations of Garbage Collection
1. Can cause slight performance overhead
📌 GC pauses may temporarily slow down real-time or latency-sensitive applications (GC pauses).2. Non-deterministic timing of memory release
📌 Programmer cannot control exactly when GC runs, making it unpredictable for time-critical operations.3. Not all unused memory may be reclaimed immediately
📌 Some objects may stay longer in memory if they are part of complex reference chains.4. Memory fragmentation issues
📌 Frequent GC can lead to fragmented memory, requiring compaction that adds overhead.Garbage Collection Process
- Mark Phase: Identify objects that are no longer referenced (unreachable)
- Sweep Phase: Remove unreferenced objects and free memory
- Compact Phase: (Optional) Compress memory to reduce fragmentation
- Finalization: Call finalize() method on objects before removal (deprecated)
- Memory Reuse: Freed memory becomes available for new object allocation
Garbage Collection Example
public class GarbageCollectionExample {
public static void main(String[] args) {
// Creating objects
String s1 = new String("Hello");
String s2 = new String("World");
// s1 is no longer referenced - eligible for GC
s1 = null;
// Request Garbage Collection (just a suggestion to JVM)
System.gc();
System.out.println("Garbage Collection requested.");
System.out.println("s2 still referenced: " + s2);
// Creating many objects to trigger GC automatically
for (int i = 0; i < 1000000; i++) {
new String("Temp String " + i);
}
System.out.println("Loop completed. GC may have run automatically.");
}
// finalize method (deprecated, but shown for understanding)
@Override
protected void finalize() throws Throwable {
System.out.println("Object is being garbage collected");
}
}