Heap vs stack, Metaspace, how garbage collection works, finalize(), GC algorithms, memory leaks, weak and soft references, and Java Flight Recorder.
Published September 25, 2026
Memory questions separate candidates who memorised a diagram from those who understand what happens when their code runs. For freshers, interviewers want clear definitions and one concrete example each. Add the "key points" when they dig deeper.
Short answer: The heap (objects), the method area / Metaspace (class metadata), and, per thread, a Java stack, a program counter register and a native method stack.
Key points to cover:
-XX:MaxMetaspaceSize.void placeOrder() {
int quantity = 3; // primitive local → lives in this method's stack frame
Order order = new Order(quantity); // reference 'order' on the stack; the Order object on the heap
} // frame popped; the Order becomes unreachable → eligible for GC
Common trap: saying "objects are stored on the stack". References can be; the objects themselves go on the heap. (The JIT's escape analysis can scalar-replace an object that never leaves a method, but that's an optimisation, not the model.)
Learn it in depth → JVM Memory Areas
Short answer: The stack is cheaper. Allocation and deallocation are just moving the stack pointer, frames are freed automatically when a method returns, and the data is thread-private and usually hot in the CPU cache. Heap objects must eventually be tracked and reclaimed by the garbage collector.
Key points to cover:
new itself.-Xss). Deep or infinite recursion causes a StackOverflowError. Running out of heap causes an OutOfMemoryError: Java heap space.Learn it in depth → JVM Memory Areas
Short answer: Garbage collection is the JVM's automatic memory management. It finds objects that are no longer reachable from any GC root and reclaims their memory, so you never free memory manually.
Key points to cover:
System.gc(), but the JVM may ignore it. Never rely on it.Common trap: saying "an object is collected when its reference is set to null". Setting a variable to null only removes one reference. The object becomes eligible once it's unreachable, and the GC decides when to reclaim it.
Learn it in depth → Garbage Collection Fundamentals
finalize() in garbage collection?Short answer: finalize() was a hook the GC could call before reclaiming an object, meant for releasing resources. It is deprecated (since Java 9, and marked for removal in Java 18), and you should never rely on it.
Key points to cover:
finalize() runs. The JVM can exit first.AutoCloseable, for deterministic cleanup.java.lang.ref.Cleaner, as a safety net for native resources.try (var reader = Files.newBufferedReader(path)) { // closed automatically, even on exceptions
return reader.readLine();
}
Common trap: describing finalize() as the way to close files or connections. Interviewers use this question to check that you know it's deprecated.
Learn it in depth → Garbage Collection Fundamentals
Short answer: The core algorithms are mark-sweep, mark-compact and copying (used for the young generation). The HotSpot collectors combine them: Serial, Parallel, G1 (the default since Java 9), and the low-pause ZGC and Shenandoah.
Key points to cover:
| Collector | Best for | Notes |
|---|---|---|
| Serial | Small heaps, single CPU, containers with 1 core | One thread; stop-the-world |
| Parallel | Batch jobs that want maximum throughput | Multi-threaded; longer pauses |
| G1 | General-purpose default | Region-based; aims for a pause target (-XX:MaxGCPauseMillis) |
| ZGC / Shenandoah | Large heaps, latency-sensitive services | Mostly concurrent; pauses of about a millisecond |
-XX:+UseZGC. Generational ZGC became the default ZGC mode in Java 23.Learn it in depth → Modern Garbage Collectors
Short answer: The GC only frees unreachable objects. A leak happens when objects you no longer need stay reachable, so they're never collected and memory keeps growing.
Key points to cover:
ThreadLocal values that aren't cleared in thread pools.hashCode/equals piling up in a HashMap.OutOfMemoryError.jcmd <pid> GC.heap_dump), and analyse it in Eclipse MAT or VisualVM. Look at the dominator tree and the paths to GC roots.class SessionRegistry {
private static final Map<String, Session> SESSIONS = new HashMap<>();
static void login(Session s) { SESSIONS.put(s.id(), s); }
// no logout/expiry → every session ever created stays reachable forever: a leak
}
Learn it in depth → Memory Leaks in Java
Short answer: They're references that don't stop an object from being collected.
Key points to cover:
WeakHashMap holds its keys weakly. An entry disappears once the key is no longer strongly referenced elsewhere. It's handy for attaching metadata to objects you don't own.ReferenceQueue) tell you after an object is collected. They're the basis of Cleaner.WeakReference<byte[]> ref = new WeakReference<>(new byte[1024]);
System.gc();
System.out.println(ref.get()); // very likely null: nothing strongly references the array
Learn it in depth → Memory Leaks in Java
Short answer: JFR is a profiling and event-recording framework built into the JVM. It captures GC pauses, allocations, lock contention, I/O, CPU samples and exceptions with very low overhead (typically around 1%), so it's safe to run in production.
Key points to cover:
-XX:StartFlightRecording=duration=60s,filename=app.jfr, or on a running process with jcmd <pid> JFR.start.Learn it in depth → GC Tuning & Diagnostics
Short answer: The Young Generation is where new objects are allocated. It's collected often, with fast minor GCs. The Old (tenured) Generation holds objects that have survived several young collections. It's collected less often, and collecting it is more expensive.
Key points to cover:
-XX:MaxTenuringThreshold), or that are too big for the survivor spaces, are promoted to the Old Generation.Learn it in depth → Garbage Collection Fundamentals
Q: What's the difference between StackOverflowError and OutOfMemoryError?
A: A StackOverflowError means one thread's stack is exhausted, almost always from runaway recursion. An OutOfMemoryError means the JVM couldn't allocate memory: heap space, Metaspace, or native memory for new threads. Both are Errors, not exceptions, and you normally don't catch them.
Q: What are -Xms and -Xmx?
A: The initial and maximum heap sizes. Many teams set them equal in production, so the heap doesn't resize at runtime. In containers, -XX:MaxRAMPercentage sizes the heap relative to the container's memory limit.
Q: What is a "stop-the-world" pause? A: A moment when all application threads are paused so the GC can work safely. Modern collectors such as G1, ZGC and Shenandoah do most of their work concurrently, to keep these pauses short.
Q: Why did Java 8 replace PermGen with Metaspace?
A: PermGen had a fixed maximum size, and applications that loaded many classes (app servers, frequent redeploys) hit OutOfMemoryError: PermGen space. Metaspace uses native memory and grows dynamically, which removed that tuning headache.
Q: Can you force garbage collection?
A: No. System.gc() is only a request, and it can be disabled with -XX:+DisableExplicitGC. Code that depends on GC timing is broken by design.