Когда вы используете StringBuilder.AppendLine / string.Формат против StringBuilder.Аппендицит?


недавно до об использовании строку.Формат.)( Часть моего ответа включала предложение использовать StringBuilder.AppendLine(строка.Формат.(..)). Джон Скит предположил, что это был плохой пример и предложил использовать комбинацию AppendLine и AppendFormat.

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

sbuilder.AppendFormat("{0} line", "First").AppendLine();
sbuilder.AppendFormat("{0} line", "Second").AppendLine();

// as opposed to:

sbuilder.AppendLine( String.Format( "{0} line", "First"));
sbuilder.AppendLine( String.Format( "{0} line", "Second"));
7 53

7 ответов:

посмотреть AppendFormat следовал по AppendLine как не только более читаемый, но и более производительный, чем вызов AppendLine(string.Format(...)).

последний создает целую новую строку, а затем добавляет ее оптом в существующий конструктор. Я не собираюсь заходить так далеко, чтобы сказать: "зачем тогда использовать StringBuilder?"но это действительно кажется немного против духа StringBuilder.

просто создайте метод расширения.

public static StringBuilder AppendLine(this StringBuilder builder, string format, params object[] args)
{
    builder.AppendFormat(format, args).AppendLine();
    return builder;
}

причины я предпочитаю это:

  • не страдает столько накладных расходов, как AppendLine(string.Format(...)), как указано выше.
  • мешает мне забыть добавить .AppendLine() часть в конце (бывает достаточно часто).
  • более читабельно (но это скорее мнение).

Если вам не нравится, что он называется "AppendLine", вы можете изменить его на "AppendFormattedLine" или что угодно хотеть. Мне нравится все выстраиваться с другими звонками в "AppendLine", хотя:

var builder = new StringBuilder();

builder
    .AppendLine("This is a test.")
    .AppendLine("This is a {0}.", "test");

просто добавьте один из них для каждой перегрузки, которую вы используете метод AppendFormat на StringBuilder.

строку.формат создает объект StringBuilder внутренне. Делая

sbuilder.AppendLine( String.Format( "{0} line", "First"));

создается дополнительный экземпляр string builder со всеми его служебными данными.


отражатель на mscorlib, Commonlauageruntimelibary, System.Строка.Формат

public static string Format(IFormatProvider provider, string format, params object[] args)
{
    if ((format == null) || (args == null))
    {
        throw new ArgumentNullException((format == null) ? "format" : "args");
    }
    StringBuilder builder = new StringBuilder(format.Length + (args.Length * 8));
    builder.AppendFormat(provider, format, args);
    return builder.ToString();
}

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

Я обычно использую:

sbuilder.AppendFormat("{0} line", "First");
sbuilder.AppendLine();
sbuilder.AppendFormat("{0} line", "Second");
sbuilder.AppendLine();

Если производительность не критична, в этом случае я бы использовал:

sbuilder.Append("First");
sbuilder.AppendLine(" line");
sbuilder.Append("Second");
sbuilder.AppendLine(" line");

(конечно, это имело бы больше смысла, если бы "первый" и " второй" где не строковые литералы)

AppendFormat () является гораздо более читаемым, чем AppendLine(String.Формат ())

Я предпочитаю эту структуру:

sbuilder.AppendFormat("{0} line\n", "First");

хотя, по общему признанию, есть что-то сказать для разделения разрывов строк.

это просто положительно ужасно просто использовать

sbuilder.AppendFormat("{0} line\n", first);

? Я имею в виду, я знаю, что это не зависит от платформы или что-то еще, но в 9 из 10 случаев он выполняет свою работу.