Uploaded image for project: 'JDK'
  1. JDK
  2. JDK-4059189

Compiler generated code for String.operator+() could avoid allocations.


    • Subcomponent:
    • Introduced In Build:
    • Introduced In Version:
    • CPU:
      generic, x86, sparc
    • OS:
      generic, solaris_2.5, solaris_7, windows_2000


      It would be cool if, in addition to transforming String.operator+() calls into calls to StringBuffer.append(), the compiler would correctly size the StringBuffer.
          E.g. the compiler currently turns

      String s = x + y + z;

      into something like

      String s = new StringBuffer().append(x).append(y).append(z).toString();

      which causes reallocation of the StringBuffer as the various append method calls are made. The compiler could transform that to

      String s = new String(x.length()+y.length()+z.length()).append(x).append(y).append(z).toString();

      (and, of course, it would be able to replace the lengths for constant Strings with a constant int). That would size the StringBuffer appropriately before the appends.
          Then, of course, we'd want to measure some real program, like javac, to see if it makes any difference.

          This RFE was suggested by Sanjoy Ghosh <sanjoy@bhopal>.

      peter.kessler@Eng 1997-06-16

      The following is copied from 4398094:

              String s1, s2;
              s1 += s2;

      we can generate slightly better code by using

              s1 = s1.append(s2);

      which allocates twice: a String and a byte[] once, compared to what we currently

              new StringBuffer().append(s1).append(s2).toString();

      which allocates at least thrice: a StringBuffer, a byte[], a String, and possibl
      e more byte[] arrays during buffer expansion. An intermediary would be

              new StringBuffer(s1).append(s2).toString();

      which would at least avoid expansion for the first append.

      Apparently the old compiler performed this optimization.

      neal.gafter@Eng 2001-07-13


      Even more fundamental optimizations are now missed:

      the method

          static String x;

          static void foo(int n) {
              x = "" + n;

      compiles to

         0 iload_0
         1 invokestatic #13 <Method java.lang.String valueOf(int)>
         4 putstatic #14 <Field java.lang.String x>
         7 return

      under 1.1.x and 1.2 but to

         0 new #2 <Class java.lang.StringBuffer>
         3 dup
         4 invokespecial #3 <Method java.lang.StringBuffer()>
         7 ldc #4 <String "">
         9 invokevirtual #5 <Method java.lang.StringBuffer append(java.lang.String)>
        12 iload_0
        13 invokevirtual #6 <Method java.lang.StringBuffer append(int)>
        16 invokevirtual #7 <Method java.lang.String toString()>
        19 putstatic #8 <Field java.lang.String x>
        22 return

      under 1.3 or later. The longer version is about twice as slow with the same
      VM, and "" + n is a pretty common idiom for converting numbers to strings.

      ###@###.### 2001-11-01


          Issue Links



              • Assignee:
                vromero Vicente Arturo Romero Zaldivar
                pbk Peter Kessler
              • Votes:
                0 Vote for this issue
                1 Start watching this issue


                • Created: