Skip to content

How does the Java compiler handle StringBuilder(a + b + c + d)?

I am dealing with an application that contains lots of legacy code. What I see very often is string concatenation using “+” within a StringBuilder argument.
Example:

StringBuilder sb = new StringBuilder("This "
        + "looks "
        + "rather "
        + "weird "
        + "to "
        + "me.") 

From what I’ve learned the compiler replaces a string concatenation that uses the + operator with StringBuilder().append().
I am afraid now the compiler will create a temporary StringBuilder to perform the concatenation then convert toString() and insert the result into the existing StringBuilder.

My Question is: Is the compiler able to optimize the nested StringBuilder away? And if not should I rewrite the code to save a few CPU cycles? It is obviously working but it hurts my eyes whenever I look at it.

Thanks for any insights!

Answer

The compiler optimizes concatenation of String literal constants:

StringBuilder sb = new StringBuilder("This "
        + "looks "
        + "rather "
        + "weird "
        + "to "
        + "me.");

is exactly equivalent, at runtime, to:

StringBuilder sb = new StringBuilder("This looks rather weird to me.");

This also applies to any String compile-time constants, not just literals.

The concern you may have read about is when using non-constants:

StringBuilder sb = new StringBuilder("This "
        + arg1
        + var2);

is equivalent to:

StringBuilder sb = new StringBuilder(new StringBuilder("This ")
        .append(arg1)
        .append(var2)
        .toString());

and it would give you better performance if you re-wrote that as:

StringBuilder sb = new StringBuilder("This ")
        .append(arg1)
        .append(var2);