Java > Memory Management in Java > Heap and Stack Memory > Understanding Java Heap
Heap Memory and String Interning
This example demonstrates the concept of String interning in Java and how it affects heap memory. String interning is a mechanism for reusing String objects by storing only one copy of each distinct String value in a special memory area called the String pool.
Code Snippet
In this code, 'str1' and 'str2' both reference the same String literal "Hello". Because of String interning, they point to the same object in the String pool (a part of the heap). 'str3' is created using the 'new' keyword, which creates a new String object on the heap, even though its value is "Hello". Therefore, 'str1' and 'str3' are different objects. 'str4' is created using 'new String("Hello")' and then '.intern()', which checks if a String with the value "Hello" exists in the String pool. If it does, it returns the reference to that object; otherwise, it adds "Hello" to the pool and returns the reference. This causes 'str1' and 'str4' to refer to the same object in the String pool. Thus, the == operator checks if both variables reference the same object on the heap.
public class StringInterning {
public static void main(String[] args) {
String str1 = "Hello";
String str2 = "Hello";
String str3 = new String("Hello");
String str4 = new String("Hello").intern();
System.out.println("str1 == str2: " + (str1 == str2)); // true
System.out.println("str1 == str3: " + (str1 == str3)); // false
System.out.println("str1 == str4: " + (str1 == str4)); // true
}
}
Concepts Behind the Snippet
"Hello"
), the JVM checks if a String with that value already exists in the String pool. If it does, the existing String object is reused. Otherwise, a new String object is created in the String pool.String.intern()
method returns a canonical representation for the String object. If the pool already contains a String equal to this String object as determined by the equals(Object)
method, then the String from the pool is returned. Otherwise, this String object is added to the pool and a reference to this String object is returned.
Real-Life Use Case
String interning can be beneficial in applications that handle a large number of duplicate String values, such as web applications that process user input or applications that read data from files. By interning Strings, you can reduce memory consumption and improve performance, especially when comparing Strings frequently. Configuration management and reading of metadata, which use the same string keys over and over, is a good use case.
Best Practices
intern()
method has some overhead. Avoid interning every String.
Interview Tip
Be prepared to discuss String interning and its impact on memory usage and performance. Understand the difference between creating Strings with literals and using the new
keyword. Be able to explain when and why you would use String interning. Also, know that prior to Java 7, the String pool was located in the PermGen space (part of the permanent generation), which had a fixed size. As of Java 7, the String pool is located in the heap, which is dynamically resized.
When to use them
Use String interning when you have a high frequency of duplicated strings and memory is limited. This is especially relevant in legacy systems with limited RAM or when processing extremely large datasets. Modern JVMs are highly optimized so the performance gains might be negligible or even negative in some cases.
Memory footprint
String interning reduces the memory footprint by sharing the same String object across multiple references. Without interning, each duplicate String would consume its own memory space on the heap. With interning, only one copy of the String is stored, saving memory. The impact on memory footprint depends on the number of duplicate strings and the length of these strings.
Alternatives
Alternatives to String interning include using a custom String pool or using a more memory-efficient data structure for storing strings, such as a Trie. Consider using libraries like Guava's ImmutableSet for storing a set of unique strings efficiently.
Pros
Cons
FAQ
-
What happens if I intern a very large String?
Interning a very large String can consume a significant amount of memory in the String pool. This can potentially impact performance and increase the risk of memory leaks if the String is not reused frequently. -
Is String interning enabled by default?
No, String interning is not enabled by default for Strings created with the 'new' keyword. You need to explicitly call theintern()
method to intern a String. String literals are automatically interned. -
Does String interning affect garbage collection?
Yes, String interning can affect garbage collection. Interned Strings are typically kept alive in the String pool for the lifetime of the application, which means they are not eligible for garbage collection unless the String pool itself is cleared.