Строки, созданные с + сцеплением, хранятся в пуле строк? - PullRequest
10 голосов
/ 12 июня 2010

Например

 String s = "Hello" + " World";

Я знаю, что в пуле "Hello" и "World" есть две строки, но входит ли "Hello World" в пул строк?

Если так, то как насчет?

String s2 = new String("Hola") + new String(" Mundo");

Сколько строк в пуле в каждом случае?

Ответы [ 6 ]

11 голосов
/ 12 июня 2010

Да, если String сформирован путем объединения двух String литералов , он также будет интернирован.

Из JLS:

Таким образом, тестовая программа, состоящая из блок компиляции (§7.3):

package testPackage;
class Test {
    public static void main(String[] args) {
        String hello = "Hello", lo = "lo";
        System.out.print((hello == "Hello") + " ");
        System.out.print((Other.hello == hello) + " ");
        System.out.print((other.Other.hello == hello) + " ");
        System.out.print((hello == ("Hel"+"lo")) + " ");
        System.out.print((hello == ("Hel"+lo)) + " ");
        System.out.println(hello == ("Hel"+lo).intern());
    }
}
class Other { static String hello = "Hello"; }
and the compilation unit:
package other;
public class Other { static String hello = "Hello"; }

производит вывод:

true
true
true
true
false
true

Важные строки - 4 и 5. 4 - это то, что вы спрашиваете в первом случае; 5 показывает, что происходит, если один не является литералом (или, в более общем смысле, константой времени компиляции).

4 голосов
/ 12 июня 2010

Я полагаю, что в первом случае компилятор будет умным и поместит объединенную строку в пул (т.е. у вас будет только 1 строка)

1 голос
/ 12 июня 2010

Для подтверждения ответа @Brian Agnew я посмотрел этот код:

public class InternTest {
    public static void main(String[] args) {
        String s = "Hello" + ", world";
        System.out.println(s);
    }
}

Такое поведение требуется для строковых литералов и константных выражений , которые оцениваются в String.

javap -c InternTest
Compiled from "InternTest.java"
public class InternTest extends java.lang.Object{
public InternTest();
  Code:
   0:   aload_0
   1:   invokespecial   #1; //Method java/lang/Object."":()V
   4:   return

public static void main(java.lang.String[]);
  Code:
   0:   ldc #2; //String Hello, world
   2:   astore_1
   3:   getstatic   #3; //Field java/lang/System.out:Ljava/io/PrintStream;
   6:   aload_1
   7:   invokevirtual   #4; //Method java/io/PrintStream.println:(Ljava/lang/String;)V
   10:  return
0 голосов
/ 01 июня 2016

Если я ошибаюсь, поправьте меня.Насколько я понимаю, в SCP будет создан только один объект.As String s = "Hello" + "World";является константой времени компиляции. Поэтому компилятор будет добавлять эти две строки только во время компиляции. И в SCP будет создан только один объект.Если вы откроете и увидите файл .class, вы найдете "HelloWorld в файле .class

0 голосов
/ 23 июля 2015
String hello = "Hello", lo = "lo";     
//  known at compile time so created in String constant pool

System.out.print((hello == "Hello") + " ");  
// known at compile time so "Hello" is same object as in hello

System.out.print((Other.hello == hello) + " ");  
// Other.hello and hello created at compile time so referenced to same object

System.out.print((other.Other.hello == hello) + " ");  
// other.Other.hello and hello created at compile time 
// so referenced to same object

System.out.print((hello == ("Hel"+"lo")) + " ");   
//  hello and  "Hel"+"lo" both were created at compile
//  time so referenced to same object

System.out.print((hello == ("Hel"+lo)) + " ");   
// value in lo was not known in runtime so didn't 
// referenced to object in hello, instead created new object in String Pool Constant

System.out.println(hello == ("Hel"+lo).intern());  
// ("Hel"+lo).intern()  using intern function told at runtime 
// to check weather same string present in String Constant Pool, 
// and if present then reference to the same string which was already present in String Constant Pool.
0 голосов
/ 12 июня 2010

Нет. Для входа в пул требуются только строковые литералы. Компиляторы могут оптимизировать объединение, а может хранить дополнительные строковые литералы в пуле.

...