Является оператором +, менее эффективным, чем StringBuffer.append()

В моей команде мы обычно выполняем строку concatentation следующим образом:

var url = // some dynamically generated URL
var sb = new StringBuffer();
sb.append("<a href='").append(url).append("'>click here</a>");

Очевидно, что следующее более читаемо:

var url = // some dynamically generated URL
var sb = "<a href='" + url + "'>click here</a>";

Но эксперты JS утверждают, что оператор + менее эффективен, чем StringBuffer.append(). Это правда?

Ответ 1

Internet Explorer - единственный браузер, который действительно страдает от этого в современном мире. (Версии 5, 6 и 7 были медленными с собакой. 8 не показывает одинаковое ухудшение.) Что еще, IE становится медленнее и медленнее, чем длиннее ваша строка.

Если у вас есть длинные строки для конкатенации, тогда обязательно используйте метод array.join. (Или некоторые обертки StringBuffer вокруг этого, для удобства чтения). Но если ваши строки коротки, не беспокойтесь.

Ответ 2

Ваш пример не очень хорош в том, что очень маловероятно, что производительность будет существенно отличаться. В вашем примере читаемость должна превзойти производительность, потому что выигрыш в производительности одного против другого является несущественным. Преимущества массива (StringBuffer) очевидны только тогда, когда вы выполняете множество конкатенаций. Даже тогда ваш пробег может сильно зависеть от вашего браузера.

Ниже приведен подробный анализ производительности, показывающий производительность с использованием всех методов конкатенации JavaScript во многих браузерах; Строковая производительность анализа

join() once, concat() once, join() for, += for, concat() for

Подробнее:
Ajaxian → Строковая производительность в IE: Array.join vs + = продолжение

Ответ 3

Да, это правда, но вам все равно. Пойдите с тем, что легче читать. Если вам нужно сравнить ваше приложение, то сосредоточьтесь на узких местах.

Я бы предположил, что конкатенация строк не будет вашим узким местом.

Ответ 4

Согласовано с Майклом Хареном.

Также рассмотрите использование массивов и объединение, если производительность действительно является проблемой.

var buffer = ["<a href='", url, "'>click here</a>"];
buffer.push("More stuff");
alert(buffer.join(""));

Ответ 5

Попробуйте следующее:

var s = ["<a href='", url, "'>click here</a>"].join("");

Ответ 6

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

Я сомневаюсь, что библиотека (написанная в JS) произведет что-нибудь более быстрое, хотя может быть и собственный объект StringBuffer. Окончательный ответ можно найти с помощью профилировщика (если вы работаете в браузере, тогда Firebug предоставит вам профилировщик JS-движка, найденный в Firefox).

Ответ 7

Как уже отмечали некоторые пользователи: это не имеет значения для небольших строк.

И новые JavaScript-движки в Firefox, Safari или Google Chrome оптимизируются, поэтому

"<a href='" + url + "'>click here</a>";

выполняется так же быстро, как

["<a href='", url, "'>click here</a>"].join("");

Ответ 8

По словам Кнута, "преждевременная оптимизация - это корень всего зла!" Небольшое отклонение в любом случае, скорее всего, не будет иметь большого эффекта в конце; Я бы выбрал более читаемый.

Ответ 9

Более простой способ позволяет людям ощущать заметное количество времени при просмотре кода, тогда как метод "более быстрый" только пропускает незаметные и, вероятно, незначительные количества времени, когда люди просматривают страницу.

Я знаю, что этот пост хромой, но я случайно разместил что-то совершенно другое, думая, что это другой поток, и я не знаю, как удалить сообщения. Мой плохой...

Ответ 10

Очень легко настроить быстрый тест и проверить изменения производительности Javascript, используя jspref.com. Наверное, этого не было, когда задавали этот вопрос. Но для людей, которые спотыкаются об этом вопросе, они должны взять на себя внимание на сайте.

Я быстро проверил различные методы конкатенации http://jsperf.com/string-concat-methods-test.

Ответ 11

Мне нравится использовать функциональный стиль, например:

function href(url,txt) {
  return "<a href='" +url+ "'>" +txt+ "</a>"
}

function li(txt) {
  return "<li>" +txt+ "</li>"
}

function ul(arr) {
  return "<ul>" + arr.map(li).join("") + "</ul>"
}

document.write(
  ul(
    [
      href("http://url1","link1"),
      href("http://url2","link2"),
      href("http://url3","link3")
    ]
  )
)

Этот стиль выглядит читаемым и прозрачным. Это приводит к созданию утилит, которые уменьшают повторение в коде.

Это также имеет тенденцию автоматически использовать промежуточные строки.

Ответ 12

Насколько я знаю, каждая конкатенация подразумевает перераспределение памяти. Таким образом, проблема заключается не в том, чтобы использовать этот оператор, а в решении сократить количество конкатенаций. Например, выполняйте конкатенации вне итерационных структур, когда сможете.

Ответ 13

Да, в соответствии с обычными критериями. E.G: http://mckoss.com/jscript/SpeedTrial.htm.

Но для маленьких струн это не имеет значения. Вам понадобятся только выступления на очень больших струнах. Что больше, в большинстве JS script, шея бутылки редко находится в строковых манипуляциях, так как ее недостаточно.

Вам лучше посмотреть манипуляции с DOM.