Lost String objects are memory wasters is it? How can garbage collection be invoked for the same?
If by "the same" you mean avoiding having two different String instances with the same content, you can use the String.intern() method.
String s = new String("test");
the string object referred by s will be on heap and the string literal "test"
will be in string pool.
Now if we do:
s = NULL;
The reference to the string object is lost and if there is no other reference to this string object it will be GC eligible. But the objects in the string pool will not be garbage collected. They are there to be reused during the lifetime of the program, to improve the performance.
In Java, it is bad practice to explicitly invoke the garbage collector. Rather, you should let the JVM decide when to run the garbage collector.
When the GC runs, it will automatically reclaim Strings that are no longer reachable. Even interned Strings will be collected in recent editions of Java.
The only way that you can "lose" Strings is if you do something like this;
String veryLarge = ... // create a very large string
String small = veryLarge.substring(0, 1);
veryLarge = null; // get rid of the last explicit reference to veryLarge.
longLived.saveString(small); // stop small from being collected.
This sequence has the unfortunate effect of leaking the character array used to represent the contents of the veryLarge
String. This happens because the substring
method uses a clever optimization to avoid creating a copy of the target String's characters. The problem is likely to bite hardest if you call intern()
on the small
String.
The way to avoid the leak is to change the 2nd line above to:
String small = new String(veryLarge.substring(0, 1));
But you should only do this sort of thing if you are going to keep references to the substrings in long-lived data structures. Otherwise, the creation of the new String is just a waste of processor cycles ... and memory.