title: StringBuilder out of memory error when working with large strings in java
body: <p>I went from <code>String test += str;</code> where <code>test</code> grew exponentially large with thousands and thousands of characters.  It took 45 minutes to run, probably from creating large strings and deleting garbage.  I then staggered the input like this which brought it to 30 seconds.  </p>
  
  <p>This seems like the cheap way to do it, but it worked well:</p>
  
  <pre><code>  if (secondDump.length() &gt; 50)
    {
       intermedDump = intermedDump + secondDump;
       secondDump = "";
    }      
  
    if (intermedDump.length() &gt; 100)
    {
       thirdDump = thirdDump + intermedDump;
       intermedDump = "";
    }
    if (thirdDump.length() &gt; 500)
    {
       fourthDump = fourthDump + thirdDump;
       thirdDump = "";
    }
    if (fourthDump.length() &gt; 1000)
    {
       fifthDump = fifthDump + fourthDump;
       fourthDump = "";
    }
    //with just this and not sixth.  Runtime&gt;&gt;&gt;&gt; : 77343
    if (fifthDump.length() &gt; 5000)
    {
       sixthDump = sixthDump + fifthDump;
       fifthDump = "";
    }
    //with just this.  Runtime&gt;&gt;&gt;&gt; : 35903Runtime&gt;&gt;&gt;&gt; : 33780
    if (sixthDump.length() &gt; 10000)
    {
       fillerDump = fillerDump + sixthDump;
       sixthDump = "";
    }
  </code></pre>
  
  <p>I then discovered that <code>StringBuilder</code> exists, and I've been trying to use it since, replacing all string operations with it.  </p>
  
  <p>The problem is, I keep getting an <code>java.lang.OutOfMemoryError</code> with a java memory heap overflow.  I think the string is just too long to store in memory as a <code>StringBuilder</code> object, because it makes about 1/50th of the progress that my previous code did before crashing with an out of memory error.  It's only working with maybe under a thousand characters.  </p>
  
  <p>Why can a string hold the entire output and this can't come close?  Also, if I append text to <code>JTextPane</code>, how much memory does that need?  If I dump the <code>StringBuilder</code> contents to <code>JTextpane</code> and keep appending and clearing <code>StringBuilder</code> that doesn't seem to work either.  </p>
  
  <p>Here is the existing code.  Page is just an object being passed:</p>
  
  <pre><code>protected void concatPlates(page PageA) throws IOException
  {
     if (backend.isFirstPage == false)
     {
        frontend.fillOutputPane("\n                                 " +
           "                                               \n", PageA);
        frontend.fillOutputPane("                                 " +
           "                                               \n", PageA);
        frontend.fillOutputPane("                                 " +
           "                                               \n", PageA);
     }
     for (int i = 0; i &lt; PLATELEN-1; i++)
     {
  
        if (arrLeftCol[i].length() == 0)
        {
           /////////////////////////////////////////////////////////
           /////////////////////////////////////////////////////////
           frontend.fillOutputPane(arrLeftCol[i].append(
             arrRightCol[i]));
        }
       else
       {
          PageA.tempStrBuff = new StringBuilder(arrLeftCol[i].substring(0,40));
          frontend.fillOutputPane(PageA.tempStrBuff.append(arrRightCol[i]));
       }
       arrLeftCol[i].append("");
       arrRightCol[i].append("");
  
       backend.isFirstPage = false;
    }
  }
  
  
  //this is the frontend class
  public static void fillOutputPane(String s, page PageA)
  {
     fillOutputPane(PageA.getStrBuf());
  }
  public static void fillOutputPane(StringBuilder stringBuild)
  {
    try
    {
       str.append(stringBuild);
    }
    catch (java.lang.OutOfMemoryError e)
    {
       System.out.println((str.length() * 16) /8);
       //System.out.println(str);
       System.out.println("out of memory error");
       System.exit(0);
    }
  }
  </code></pre>
  
  <p>Here is the error:</p>
  
  <pre><code>Exception in thread "AWT-EventQueue-0" java.lang.OutOfMemoryError: Java heap space
  at java.util.Arrays.copyOf(Unknown Source)
  at java.lang.AbstractStringBuilder.expandCapacity(Unknown Source)
  at java.lang.AbstractStringBuilder.append(Unknown Source)
  at java.lang.StringBuilder.append(Unknown Source)
  at java.lang.StringBuilder.append(Unknown Source)
  at backend.fill(backend.java:603)
  at frontend$openL.actionPerformed(frontend.java:191)
  at javax.swing.AbstractButton.fireActionPerformed(Unknown Source)
  at javax.swing.AbstractButton$Handler.actionPerformed(Unknown Source)
  at javax.swing.DefaultButtonModel.fireActionPerformed(Unknown Source)
  at javax.swing.DefaultButtonModel.setPressed(Unknown Source)
  at javax.swing.AbstractButton.doClick(Unknown Source)
  at javax.swing.plaf.basic.BasicMenuItemUI.doClick(Unknown Source)
  at javax.swing.plaf.basic.BasicMenuItemUI$Handler.mouseReleased(Unknown Source)
  at java.awt.Component.processMouseEvent(Unknown Source)
  at javax.swing.JComponent.processMouseEvent(Unknown Source)
  at java.awt.Component.processEvent(Unknown Source)
  at java.awt.Container.processEvent(Unknown Source)
  at java.awt.Component.dispatchEventImpl(Unknown Source)
  at java.awt.Container.dispatchEventImpl(Unknown Source)
  at java.awt.Component.dispatchEvent(Unknown Source)
  at java.awt.LightweightDispatcher.retargetMouseEvent(Unknown Source)
  at java.awt.LightweightDispatcher.processMouseEvent(Unknown Source)
  at java.awt.LightweightDispatcher.dispatchEvent(Unknown Source)
  at java.awt.Container.dispatchEventImpl(Unknown Source)
  at java.awt.Window.dispatchEventImpl(Unknown Source)
  at java.awt.Component.dispatchEvent(Unknown Source)
  at java.awt.EventQueue.dispatchEventImpl(Unknown Source)
  at java.awt.EventQueue.access$000(Unknown Source)
  at java.awt.EventQueue$1.run(Unknown Source)
  at java.awt.EventQueue$1.run(Unknown Source)
  at java.security.AccessController.doPrivileged(Native Method)
  </code></pre>
  
  <p>I think this is what a stack trace is:</p>
  
  <pre><code>java.lang.Exception: Stack trace
  at java.lang.Thread.dumpStack(Unknown Source)
  at frontend.fillOutputPane(frontend.java:385)
  at page.concatPlates(page.java:105)
  at backend.setPlate(backend.java:77)
  at backend.fill(backend.java:257)
  at frontend$openL.actionPerformed(frontend.java:191)
  at javax.swing.AbstractButton.fireActionPerformed(Unknown Source)
  at javax.swing.AbstractButton$Handler.actionPerformed(Unknown Source)
  at javax.swing.DefaultButtonModel.fireActionPerformed(Unknown Source)
  at javax.swing.DefaultButtonModel.setPressed(Unknown Source)
  at javax.swing.AbstractButton.doClick(Unknown Source)
  at javax.swing.plaf.basic.BasicMenuItemUI.doClick(Unknown Source)
  at javax.swing.plaf.basic.BasicMenuItemUI$Handler.mouseReleased(Unknown Source)
  at java.awt.Component.processMouseEvent(Unknown Source)
  at javax.swing.JComponent.processMouseEvent(Unknown Source)
  at java.awt.Component.processEvent(Unknown Source)
  at java.awt.Container.processEvent(Unknown Source)
  at java.awt.Component.dispatchEventImpl(Unknown Source)
  at java.awt.Container.dispatchEventImpl(Unknown Source)
  at java.awt.Component.dispatchEvent(Unknown Source)
  at java.awt.LightweightDispatcher.retargetMouseEvent(Unknown Source)
  at java.awt.LightweightDispatcher.processMouseEvent(Unknown Source)
  at java.awt.LightweightDispatcher.dispatchEvent(Unknown Source)
  at java.awt.Container.dispatchEventImpl(Unknown Source)
  at java.awt.Window.dispatchEventImpl(Unknown Source)
  at java.awt.Component.dispatchEvent(Unknown Source)
  at java.awt.EventQueue.dispatchEventImpl(Unknown Source)
  at java.awt.EventQueue.access$000(Unknown Source)
  at java.awt.EventQueue$1.run(Unknown Source)
  at java.awt.EventQueue$1.run(Unknown Source)
  at java.security.AccessController.doPrivileged(Native Method)
  at java.security.AccessControlContext$1.doIntersectionPrivilege(Unknown Source)
  at java.security.AccessControlContext$1.doIntersectionPrivilege(Unknown Source)
  at java.awt.EventQueue$2.run(Unknown Source)
  at java.awt.EventQueue$2.run(Unknown Source)
  at java.security.AccessController.doPrivileged(Native Method)
  at java.security.AccessControlContext$1.doIntersectionPrivilege(Unknown Source)
  at java.awt.EventQueue.dispatchEvent(Unknown Source)
  at java.awt.EventDispatchThread.pumpOneEventForFilters(Unknown Source)81240560
  at java.awt.EventDispatchThread.pumpEventsForFilter(Unknown Source)
  at java.awt.EventDispatchThread.pumpEventsForHierarchy(Unknown Source)
  at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
  at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
  at java.awt.EventDispatchThread.run(Unknown Source)
  </code></pre>