4

Say I have this String expression

String hi = "Tom" + "Brady" + "Goat"

I know that the String pool "allows a runtime to save memory by preserving immutable strings in a pool" String Pool

How many strings will be created in the string pool?

My initial guess was 5 - "Tom", "Brady", "Goat", "TomBrady","TomBradyGoat", because of the order of operations of String concatenation (left to right?) or is it only the final result, "TomBradyGoat", that is stored in the String pool?

Community
  • 1
  • 1
committedandroider
  • 7,124
  • 12
  • 48
  • 114

4 Answers4

5

What you have here is a constant expression, as defined by the JLS, Section 15.28.

A constant expression is an expression denoting a value of primitive type or a String that does not complete abruptly and is composed using only the following:

  • Literals of primitive type and literals of type String (§3.10.1, §3.10.2, §3.10.3, §3.10.4, §3.10.5)

  • Casts to primitive types and casts to type String (§15.16)

  • The unary operators +, -, ~, and ! (but not ++ or --) (§15.15.3, §15.15.4, §15.15.5, §15.15.6)

  • The multiplicative operators *, /, and % (§15.17)

  • The additive operators + and - (§15.18)

(other possibilities)

The compiler determines that the expression "Tom" + "Brady" + "Goat" is a constant expression, so it will evaluate the expression itself to "TomBradyGoat".

The JVM will have only one string in the string pool, "TomBradyGoat".

Community
  • 1
  • 1
rgettman
  • 167,281
  • 27
  • 248
  • 326
3

At runtime, that piece of code will translate into a single String object. The compiler will take care of concatenation at compile time and add a single value in the constants pool.

Sotirios Delimanolis
  • 252,278
  • 54
  • 635
  • 683
2

The other answers explain well why only 1 String is added to the String pool. But if you want to check and make some tests by yourself you can take a look on the bytecode to see the number of String created and added to the string pool. Ex:

Ex1:

public static void main(String[] args) {
    String hi = "Tom" + "Brady" + "Goat";
}

ByteCode:

  // access flags 0x9
  public static main(String[]) : void
   L0
    LINENUMBER 6 L0
    LDC "TomBradyGoat"
    ASTORE 1
   L1
    LINENUMBER 7 L1
    RETURN
   L2
    LOCALVARIABLE args String[] L0 L2 0
    LOCALVARIABLE hi String L1 L2 1
    MAXSTACK = 1
    MAXLOCALS = 2

As you can see only 1 String is created

Ex2:

public static void main(String[] args) {
        String str1 = "Tom";
        String str2 = "Brady";
        String str3 = "Goat";
        String str = str1 + str2 + str3;
}

Bytecode:

  // access flags 0x9
  public static main(String[]) : void
   L0
    LINENUMBER 6 L0
    LDC "Tom"
    ASTORE 1
   L1
    LINENUMBER 7 L1
    LDC "Brady"
    ASTORE 2
   L2
    LINENUMBER 8 L2
    LDC "Goat"
    ASTORE 3
   L3
    LINENUMBER 9 L3
    NEW StringBuilder
    DUP
    ALOAD 1: str1
    INVOKESTATIC String.valueOf (Object) : String
    INVOKESPECIAL StringBuilder.<init> (String) : void
    ALOAD 2: str2
    INVOKEVIRTUAL StringBuilder.append (String) : StringBuilder
    ALOAD 3: str3
    INVOKEVIRTUAL StringBuilder.append (String) : StringBuilder
    INVOKEVIRTUAL StringBuilder.toString () : String
    ASTORE 4
   L4
    LINENUMBER 10 L4
    RETURN
   L5
    LOCALVARIABLE args String[] L0 L5 0
    LOCALVARIABLE str1 String L1 L5 1
    LOCALVARIABLE str2 String L2 L5 2
    LOCALVARIABLE str3 String L3 L5 3
    LOCALVARIABLE str String L4 L5 4
    MAXSTACK = 3
    MAXLOCALS = 5

As you can see 4 Strings are created

M. Abbas
  • 6,073
  • 4
  • 30
  • 40
  • @committedandroider: Try `javap -c com.mypackage.MyClass`; see http://stackoverflow.com/questions/3315938/is-it-possible-to-view-bytecode-of-class-file – Jonik Feb 27 '15 at 08:07
-1

As other people have mentioned, the compiler is good enough to optimize that very simple example, but if you have more complicated functionality (which is probably what you care about), it might not. For example:

String a = "Tom";
String b = "Brady";
String c = a;
c += b;

This would result in 3 strings being created.

Necreaux
  • 8,456
  • 7
  • 22
  • 43
  • It's not a matter of 'good enough'. The compiler is *required* by the JLS to treat the OP's expression as a constant expression and create a single string. – user207421 Feb 25 '15 at 21:44