Java OutOfMemoryError with StringBuilder or StringBuffer
StringBuilder or StringBuffer are used for string manipulations. Yet they fail some times.
Both the final classes are the extension for packaged scoped abstract class named "java.lang.AbstractStringBuilder". These builder/buffer classes holds character array and append or manipulate this char[] each time we perform operations on it. The default char[] size is 16 although this can be specified while creating the object. When append() method is called upon StringBuilder/StringBuffer, the capacity of this char[] is checked if the String/char/any other object can be added to ongoing char[] buffer. If the character buffer size is less. I.e. not sufficient enough to append more, the capacity is doubled . Lets say its capacity was 16, and not sufficient to add more, than the the capacity is increased by doubling the size of current buffer length. This keeps happening when you keep on appending stuffs to it. Common case is while reading a file and storing it inside memory in form of a StringBuilder. You never know what the size of file could be. when size isn't sufficient for the StringBuilder, buffer size is doubled and this keeps growing. A point will reach when System is not able to
allocate enough space for the buffer.
The problem with StringBuilder I see is it doubles the capacity from current length. Lets say the internal char buffer length is 65000 and more 100 chars has to be added than the buffer capacity is doubled to 65000 * 2. If we dive into the code of Arrays.copyOf() method line no# 2882. It tries to create a new char[] of size 65000 * 2 (in our case).
char[] copy = new char[newLength];
And this will throw Error if the Java Virtual machine does not have enough to allocate.
How do we get rid of such OutOfMemoryError? Decide what are we going to hold in StringBuilder's class buffer. It is always better to use StringBuilder/StringBuffer instead of performing string operations like
String myString = "x" + "y" + "z"
ut if we have to read some file and then write that into some file back again then, go for Streams. This is what the purpose of Streams or Writer/Reader are. Decide the buffer length and use streams to work in such cases. If that is not workable in the situation, than the common approach for solving java.lang.OutOfMemoryError is to increase the JVM memory via parameters like -Xmx256m
String manipulation is always a performance over head. implement the best practices and best applicable solution as when to use normal String concatenations or go for StringBuilder or Streams
A mutable sequence of characters. This class provides an API compatible with StringBuffer, but with no guarantee of synchronization. This class is designed for use as a drop-in replacement for StringBuffer in places where the string buffer was being used by a single thread (as is generally the case). Where possible, it is recommended that this class be used in preference to StringBuffer as it will be faster under most implementations.
The principal operations on a StringBuilder are the append and insert methods, which are overloaded so as to accept data of any type. Each effectively converts a given datum to a string and then appends or inserts the characters of that string to the string builder. The append method always adds these characters at the end of the builder; the insert method adds the characters at a specified point.