Understanding Heap and Stack Memory
Disclaimer
It’s important to note that this topic is broader than what is covered in this article. The goal is to have a basic understanding of the heap and stack memory.
Heap Memory
Heap memory is shared across the entire application and threads. Any thread can access objects stored in the heap, as long as it holds a valid reference to them. Objects in Java are created in the heap, while references to those objects are typically stored on the stack within a thread’s method execution context. Heap memory management is more complex and handled automatically by the JVM through generational garbage collection. This includes handling object allocation, tracking object lifetimes, and reclaiming memory when objects are no longer reachable.
Note: Although heap memory is shared between threads, objects can only be accessed through references that are in scope, and concurrent access must be managed carefully to avoid race conditions.
Stack Memory
Stack memory is private to each thread and is only accessible within that thread's execution context. This is the part of the memory where method frames, local variables and object references are stored. In terms of memory allocation, it is referred to as a temporary storage. Stack memory uses a LIFO(Last In, First Out) structure to manage memory. Accessing variables stored in the stack is typically faster due to its structure. However, the stack has a much smaller memory size compared to the heap.
Functional Example
class Example{
public static void main(String [] args)
{
Object ball = new Object();
hit(ball);
}
private static void hit(Object ball) {
System.out.println("The red " + ball + " is dangerous");
}
}
When the above program is executed, the main() method is assigned a stack frame in memory. An object is then initialized in the next line and this will be stored in the heap memory. We then pass a reference to the ball object into the hit method. The reference to the object is stored on the stack frame of the hit method.
What happens here:
main()is pushed onto the stackball(the object) is created in the heapThe reference to
ballis stored in the stack frame ofmain()When
hit(ball)is called:A new stack frame is created
The reference to
ballis passed and stored in that frame
JVM Options For Stack and Heap Memory
Heap
When the heap memory is full, you see an error that reads OutOfMemoryError: Java heap space. To prevent this, you can increase the initial and maximum heap size using -Xms and -Xmx Java options. Xms sets how much heap the JVM starts with and Xmx caps how large the heap can grow.
Stack
Stack allocates memory per thread. Each thread gets its own stack for method calls and local variables. Java runtime throws StackOverflowError when the call stack exceeds its allocated size, usually because of an infinite recursion. To prevent this, you can increase the stack size using -Xss .
Note
Making changes to the memory should be solely based on observability and data as opposed to guesswork. You should scale as needed and it’s okay to begin with defaults if you want.
Key Differences Between Stack and Heap
| Heap | Stack |
|---|---|
| Stores Objects and instance variables | Stores Methods and local variables |
| Available as long as the variable is referenced | Available when the method is executing |
| Managed by Garbage collector | Managed using LIFO |
| Slower to access than the stack | Very fast to access |


