string vs StringBuilder in C#: when to use which
A string never changes once created; every "modification" produces a new string. A StringBuilder keeps a growable buffer and modifies it in place. The rule of thumb: use StringBuilder when you build text in a loop, and plain strings almost everywhere else.
Immutability in practice
string s = "Hello";
string t = s.ToUpper(); // s is still "Hello"; t is a new string "HELLO"
s += " world"; // creates a third string and points s at it
Immutability makes strings safe to share between threads and to use as dictionary keys. The cost appears in loops:
// Quadratic: each += copies everything built so far
string csv = "";
foreach (var row in rows) csv += row.Id + "," + row.Name + "\n";
// Linear: appends into one buffer
var sb = new StringBuilder();
foreach (var row in rows) sb.Append(row.Id).Append(',').Append(row.Name).Append('\n');
string csv2 = sb.ToString();
With 10,000 rows, the first version copies the growing text 10,000 times; the second copies each piece about once (the buffer occasionally doubles in size). The difference grows with the number of iterations.
When plain strings are fine
- A fixed number of pieces in one expression:
a + b + c + dcompiles to a singlestring.Concatcall, which allocates once. - Interpolation:
$"{first} {last}"is clear and efficient. - Joining a collection:
string.Join(", ", names)is shorter and as fast as a builder.
Comparison
| string | StringBuilder | |
|---|---|---|
| Mutable | No | Yes |
| Thread-safe for reading | Yes | No (instances are not thread-safe) |
| Best for | Values, keys, a few concatenations | Building text in loops, many appends |
| Equality | Compares text (== overloaded) | Reference; compare ToString() results |
| Namespace | System | System.Text |
StringBuilder tips
- If you know roughly how big the result will be, set an initial capacity:
new StringBuilder(64 * rows.Count). - Chain
Appendcalls and append characters aschar(',') rather than one-character strings. AppendFormatandAppendLineexist; on .NET 6+,sb.Append($"…")appends interpolated text without an intermediate string.- Call
ToString()once at the end.
In ASP.NET pages
Building an HTML fragment or a CSV export row by row is the typical use, as in Send a GridView by e-mail and Export a file list to CSV. Whatever builds the text, encode user data (HttpUtility.HtmlEncode) before appending it to HTML. And for SQL, never build statements by appending values: use parameters (SQL injection).
The alias question, string or String, is covered in string vs String.
Official documentation
- Microsoft Learn: StringBuilder class, Using the StringBuilder class in .NET
- Microsoft Learn: Strings and string literals (C# programming guide), How to concatenate multiple strings