Skip to content

Commit cf2645f

Browse files
TheTonttutig
authored andcommitted
StringExtensions.ToString(IEnumerable<Rune>) use rented array as alternative buffer
1 parent 9b78961 commit cf2645f

File tree

2 files changed

+16
-5
lines changed

2 files changed

+16
-5
lines changed

Benchmarks/Text/StringExtensions/ToStringEnumerable.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ public string Previous (IEnumerable<Rune> runes, int len)
2222
}
2323

2424
/// <summary>
25-
/// Benchmark for current implementation with stackalloc char buffer and
25+
/// Benchmark for current implementation with char buffer and
2626
/// fallback to rune chars appending to StringBuilder.
2727
/// </summary>
2828
/// <param name="runes"></param>

Terminal.Gui/Text/StringExtensions.cs

+15-4
Original file line numberDiff line numberDiff line change
@@ -127,18 +127,22 @@ public static string ToString (IEnumerable<Rune> runes)
127127
const int maxCharsPerRune = 2;
128128
const int maxStackallocTextBufferSize = 1048; // ~2 kB
129129

130-
// Use stackalloc buffer if rune count is easily available and the count is reasonable.
130+
// If rune count is easily available use stackalloc buffer or alternatively rented array.
131131
if (runes.TryGetNonEnumeratedCount (out int count))
132132
{
133133
if (count == 0)
134134
{
135135
return string.Empty;
136136
}
137137

138-
int maxRequiredTextBufferSize = count * maxCharsPerRune;
139-
if (maxRequiredTextBufferSize <= maxStackallocTextBufferSize)
138+
char[]? rentedBufferArray = null;
139+
try
140140
{
141-
Span<char> textBuffer = stackalloc char[maxRequiredTextBufferSize];
141+
int maxRequiredTextBufferSize = count * maxCharsPerRune;
142+
Span<char> textBuffer = maxRequiredTextBufferSize <= maxStackallocTextBufferSize
143+
? stackalloc char[maxRequiredTextBufferSize]
144+
: (rentedBufferArray = ArrayPool<char>.Shared.Rent(maxRequiredTextBufferSize));
145+
142146
Span<char> remainingBuffer = textBuffer;
143147
foreach (Rune rune in runes)
144148
{
@@ -149,6 +153,13 @@ public static string ToString (IEnumerable<Rune> runes)
149153
ReadOnlySpan<char> text = textBuffer[..^remainingBuffer.Length];
150154
return text.ToString ();
151155
}
156+
finally
157+
{
158+
if (rentedBufferArray != null)
159+
{
160+
ArrayPool<char>.Shared.Return (rentedBufferArray);
161+
}
162+
}
152163
}
153164

154165
// Fallback to StringBuilder append.

0 commit comments

Comments
 (0)