What are the consequences of String immutability?
The problem of excessive allocation in loops leads to:
Basic Level
Positive consequences
- Strings are thread-safe — can be passed between threads without issues
- Memory savings — identical strings stored once (String Pool)
- Can be used as HashMap keys — hashCode doesn’t change
Negative consequences
- Every operation creates a new object — this consumes memory
- Concatenation in a loop is a bad idea:
String s = ""; for (int i = 0; i < 1000; i++) { s += i; // 1000 objects created! }
The solution — StringBuilder
StringBuilder sb = new StringBuilder();
for (int i = 0; i < 1000; i++) {
sb.append(i); // One object, in-place modifications
}
String s = sb.toString();
Intermediate Level
Performance impact
The problem of excessive allocation in loops leads to:
- Filling of Young Generation (Eden space)
- Increased frequency of GC cycles
- Memory fragmentation
Rule: for mass modifications, always use:
- StringBuilder — single-threaded, fast
- StringBuffer — multi-threaded, slower
Security consequences: working with passwords
A String object with a password will remain in memory until GC decides to collect it. You cannot programmatically “wipe” its contents.
Recommendation: for sensitive data, use char[]:
char[] password = console.readPassword();
// Pattern for console applications (System.console().readPassword()).
// For web applications — other approaches (HTTPS, secure cookie, don't store password).
// ... used it
Arrays.fill(password, (char) 0); // zeroed out
Code design
String immutability encourages a functional style — methods don’t modify arguments but return results. This makes code predictable and easily testable (Pure Functions).
Advanced Level
GC Pressure and optimizations
String immutability creates GC load, but:
- Short-lived strings are efficiently cleaned up in Minor GC
- String Deduplication is only available with G1 GC (flag
-XX:+UseStringDeduplication). Not supported for ZGC/Shenandoah. - Compact Strings (Java 9+) reduce memory consumption by 50% for Latin characters
Security nuances
TOCTOU attack (Time-of-Check to Time-of-Use): impossible with immutable strings, because a string cannot change between the check and the use.
But there’s a flip side:
- Strings with passwords/tokens remain in heap dumps in plain text
- Strings can be swapped to disk by the OS
- String interning makes strings long-lived (Old Gen)
Impact on JIT optimizations
The JIT compiler can aggressively optimize string-related code:
- Constant folding — computing constant expressions at compile time
- String intrinsics — native methods for
equals(),hashCode(),indexOf() - Escape analysis — eliminating unnecessary allocations during concatenation
Summary for Advanced
- Immutability is “expensive but reliable”: 1000 concatenations = 1000 objects on the heap; StringBuilder = 1 object.
- The main cost — GC load from careless loop usage
- For secrets, use
char[]/byte[]that can be zeroed out - For high-load systems, it’s important to understand the difference between
StringandStringBuilder - When working with secrets, remember the “residual” presence of strings in the heap
Interview Cheat Sheet
Must know:
- Positive: thread-safety, String Pool, stable HashMap keys
- Negative: every change = new object, concatenation in a loop creates N objects
- StringBuilder — the solution for mass modifications (single-threaded, fast)
- Passwords in String — bad practice: cannot be zeroed, remains in heap dump
- For secrets use
char[]+Arrays.fill(password, (char) 0) - String Deduplication — only G1 GC (
-XX:+UseStringDeduplication), not ZGC/Shenandoah - JIT optimizations: constant folding, string intrinsics, escape analysis
Frequent follow-up questions:
- Why is concatenation in a loop bad? — 1000 iterations = 1000 objects on the heap → GC pressure
- Why can’t passwords be stored in String? — Cannot be programmatically wiped, remains in memory until GC
- What is a TOCTOU attack? — Time-of-Check to Time-of-Use: string changes between check and use; impossible with immutable String
- When to use StringBuilder vs String? — StringBuilder for loops and mass modifications, String for storage and transfer
Red flags (DO NOT say):
- “String += in a loop is fine” — for 1000 iterations that’s 1000 objects
- “Passwords can be stored in String” — they cannot be securely removed from memory
- “char[] is always safer than String” —
char[]can also be in heap dump; but it can be zeroed out - “String Deduplication works everywhere” — only G1 GC with the flag
Related topics:
- [[4. Why is the String class immutable]]
- [[18. How does String pool work and how is it related to immutability]]
- [[19. Can you change a String value via reflection]]
- [[23. How does immutability affect performance]]