Подтвердить что ты не робот

String builder против конкатенации строк

Какова польза и компромисс между использованием построителя строк по конкатенации чистой строки?

new StringBuilder(32).append(str1)
                     .append(" test: ")
                     .append(val)
                     .append(" is changed")
                     .toString();

vs say

str1 + " test: " + val + " is changed".

str1 - это случайная строка из 10 символов. str2 - это случайная 8-символьная строка.

4b9b3361

Ответ 1

В вашем тривиальном примере нет никого, потому что компилятор использует StringBuilder для выполнения конкатенации строк. Однако, если конкатенация произошла в цикле, компилятор мог создать несколько объектов StringBuilder и String. Например:

String s= "" ;
for(int i= 0 ; i < 10 ; i++ )
    s+= "a" ;

Каждый раз, когда выполняется строка 3 выше, создается объект StringBuilder, содержимое s добавлено, "a" добавлено, а затем StringBuilder преобразуется в строку, которая должна быть привязана к s. Всего 10 StringBuilder и 10 String s.

Обратно, в

StringBuilder sb= new StringBuilder() ;
for(int i= 0 ; i < 10 ; i++ )
    sb.append( "a" );
String s= sb.toString() ;

Созданы только 1 StringBuilder и 1 String.

Основная причина этого заключается в том, что компилятор не мог быть достаточно умным, чтобы понять, что первый цикл эквивалентен второму и генерирует более эффективный (байтовый) код. В более сложных случаях это невозможно даже для самого умного компилятора. Если вам абсолютно нужна эта оптимизация, вы должны ввести ее вручную, используя явно StringBuilder.

Ответ 2

Быстрый ответ - это производительность: когда вы используете собственные классы String, он работает с неизменяемыми строками, что означает, что когда вы пишете

  String line = "java";
  String sufix = " is awesome";
  line = line + sufix;

он создаст две строки: "java" и "is awesome", чем создать новую третью строку "java is awesome" из предыдущих двух ( "java" и "is awesome" ), которые позже, вероятно, будут удалены сборщик мусора (потому что они больше не используются в приложении). Это медленное решение.

Более быстрое решение - это устройство класса StringBuffer, которое через интеллектуальные алгоритмы, которые предоставляют буфер (что очевидно из его имени) для слияния строк, и в результате не удалит исходную строку во время процесса конкатенации.

Если вы пишете однопоточное приложение (без проблем совпадения, при котором несколько потоков обращаются к одному объекту), лучше применять StringBuilder, который имеет даже более высокую производительность, чем исходный класс StringBuffer.