sirve qué que para example clase appendformat .net stringbuilder

.net - qué - stringbuilder java 8



¿En qué momento usar un StringBuilder se vuelve insignificante o una sobrecarga? (7)

Recientemente me he encontrado usando StringBuilder para todas las concatenaciones de cadenas, grandes y pequeñas, sin embargo, en una prueba de rendimiento reciente, cambié el stringOut = string1 + "." De un colega . concatenación de estilo string2 (utilizada en un bucle de 10000x + con el generador de cadenas cada vez) para un StringBuilder solo para ver qué diferencia haría en una concatenación menor.

Descubrí que, durante muchas ejecuciones de la prueba de rendimiento, el cambio fue insignificantemente mayor o menor, independientemente de la concatenación o de StringBuilder (restablecer que esto era para concatenaciones pequeñas ).

¿En qué punto el ''newing up'' de un objeto StringBuilder niega los beneficios de usar uno?


Desde MSDN :

[E] l clase String es preferible para una operación de concatenación si se concatena un número fijo de objetos String. En ese caso, las operaciones de concatenación individuales incluso podrían combinarse en una única operación por el compilador. Un objeto StringBuilder es preferible para una operación de concatenación si se concatenan un número arbitrario de cadenas; por ejemplo, si un bucle concatena un número aleatorio de cadenas de entrada del usuario.

Supongo que la respuesta es "depende": si está concatenándose dentro de un bucle con más de un puñado de iteraciones, un StringBuilder casi siempre ofrecerá un mejor rendimiento, pero la única forma de saberlo con certeza es con un perfil real.


Hay un interesante artículo sobre esto en Coding Horror . Jeff obtuvo los siguientes resultados para 100,000 iteraciones en un núcleo dual Core 2 Duo a 3.5 GHz:

Simple Concatenation - 606 ms String.Format - 665 ms string.Concat - 587 ms String.Replace - 979 ms StringBuilder - 588 ms


A veces vale la pena mirar la documentación :

La ejecución de una operación de concatenación para un objeto String o StringBuilder depende de la frecuencia con la que se produce una asignación de memoria. Una operación de concatenación de cadenas siempre asigna memoria, mientras que una operación de concatenación StringBuilder solo asigna memoria si el búfer de objetos StringBuilder es demasiado pequeño para acomodar los datos nuevos. En consecuencia, la clase String es preferible para una operación de concatenación si se concatena un número fijo de objetos String. En ese caso, las operaciones de concatenación individuales incluso podrían combinarse en una única operación por el compilador. Un objeto StringBuilder es preferible para una operación de concatenación si se concatenan un número arbitrario de cadenas; por ejemplo, si un bucle concatena un número aleatorio de cadenas de entrada del usuario.

En su ejemplo, solo hay una sola cadena de concatenación por salida, por lo que StringBuilder no le gana nada. Debería utilizar StringBuilder en los casos en los que agregue a la misma cadena muchas veces, por ejemplo:

stringOut = ... for(...) stringOut += "." stringOut += string2


Estoy seguro de que tengo otra respuesta donde publiqué solo un enlace a mi artículo y luego su resumen, pero aquí vamos de nuevo.

  • Definitivamente use StringBuilder cuando esté concatenándose en un bucle no trivial, especialmente si no sabe con certeza (en tiempo de compilación) cuántas iteraciones realizará a través del bucle. Por ejemplo, leer un archivo de un personaje a la vez, construir una cadena sobre la marcha con el operador + = es potencialmente un suicidio de rendimiento.

  • Definitivamente use el operador de concatenación cuando pueda (legible) especificar todo lo que necesita concatenarse en una declaración. (Si tiene una serie de elementos para concatenar, considere llamar a String.Concat explícitamente - o String.Join si necesita un delimitador).

  • No tenga miedo de dividir los literales en varios bits concatenados; el resultado será el mismo. Puede ayudar a la legibilidad dividiendo un literal largo en varias líneas, por ejemplo, sin dañar el rendimiento.

  • Si necesita los resultados intermedios de la concatenación para algo que no sea alimentar la próxima iteración de concatenación, StringBuilder no lo ayudará. Por ejemplo, si crea un nombre completo a partir de un nombre y un apellido, y luego agrega una tercera información (el alias, tal vez) hasta el final, solo se beneficiará de usar StringBuilder si no lo hace necesita la cadena (nombre + apellido) para otro fin (como lo hacemos en el ejemplo que crea un objeto Person ).

  • Si solo tiene algunas concatenaciones que hacer, y realmente desea hacerlas en declaraciones separadas, en realidad no importa qué camino tomar. El camino que sea más eficiente dependerá de la cantidad de concatenaciones, los tamaños de cadena implicados y el orden en que están concatenados. Si realmente crees que esa parte del código es un cuello de botella de rendimiento, perfila o compara ambos aspectos.


La regla que sigo es -

Use un StringBuilder cuando se desconoce el número de concatenaciones en tiempo de compilación.

Entonces, en su caso, cada StringBuilder solo se agregaba unas pocas veces y luego se descartaba. Eso no es realmente lo mismo que algo así

string s = String.Empty; for (int i = 0; i < 10000; ++i) { s += "A"; }

Donde usar un StringBuilder mejoraría drásticamente el rendimiento porque de lo contrario estaría asignando constantemente memoria nueva.


Mi regla de oro es simple.

  1. Si razonablemente puede escribir una sola expresión que produzca el final, entonces use + .
  2. Si no puede (debido a su tamaño o variabilidad), entonces use StringBuilder.

En mi experiencia, expresiones como:

"Id: " + item.id + " name: " + item.name

puede escribirse y entenderse mucho más fácilmente que:

StringBuilder sb = new StringBuilder(); sb.append("Id: ").append(item.id); sb.append(" name: ").append(item.name);

(seguido de usar la cadena de sb donde se habría escrito la expresión anterior), y funciona igualmente bien (pista: ¡mire el código compilado para ver por qué!)

Por otro lado, cuando hay necesidad de acumular una cadena a lo largo del tiempo (a medida que se ejecuta el programa) o espacio (formado por valores provenientes de diferentes partes del código), de una manera que no es práctico escribir como una expresión de una sola línea , luego StringBuilder evita la sobrecarga (tiempo y agitación de la memoria) de:

String s = somethingExpression; ... s += someOtherExpression; ... s += yetAnotherExpression; ...


De Dot Net Perls :

Cuándo usar StringBuilder?

StringBuilder es completamente una optimización, y no ofrece mejoras lógicas para la cadena Concat aparte de su implementación interna. Dicho esto, es fundamental usarlo correctamente en sus aplicaciones y sitios web de alto rendimiento.

A veces, está bien utilizar pequeños bucles de 4 o menos iteraciones con cadena simple de Concats. Sin embargo, en casos extremos esto puede ser desastroso. Planifique sus casos extremos con StringBuilder.