Skip to content

Commit fc3e108

Browse files
authored
General improvements and fixes in StringBuilder (#191)
1 parent 648f335 commit fc3e108

File tree

2 files changed

+930
-483
lines changed

2 files changed

+930
-483
lines changed

Tests/NFUnitTestStringBuilder/StringBuilderTests.cs

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -443,6 +443,74 @@ public void Clear_AtMaxCapacity_CapacityStaysUnchanged()
443443
builder.Clear();
444444
Assert.AreEqual(14, builder.Capacity);
445445
}
446+
447+
[TestMethod]
448+
[DataRow(1)]
449+
[DataRow(10000)]
450+
public void Clear_AppendAndInsertBeforeClearManyTimes_CapacityStaysWithinRange(int times)
451+
{
452+
var builder = new StringBuilder();
453+
var originalCapacity = builder.Capacity;
454+
var s = new string(' ', 10);
455+
int oldLength = 0;
456+
for (int i = 0; i < times; i++)
457+
{
458+
builder.Append(s);
459+
builder.Append(s);
460+
builder.Append(s);
461+
builder.Insert(0, s, 1);
462+
builder.Insert(0, s, 1);
463+
oldLength = builder.Length;
464+
465+
builder.Clear();
466+
}
467+
Assert.IsTrue(builder.Capacity >= 1 && builder.Capacity <= oldLength * 1.2);
468+
}
469+
470+
[TestMethod]
471+
public void Clear_InitialCapacityMuchLargerThanLength_CapacityReducedToInitialCapacity()
472+
{
473+
var builder = new StringBuilder(100);
474+
var initialCapacity = builder.Capacity;
475+
builder.Append(new string('a', 40));
476+
builder.Insert(0, new string('a', 10), 1);
477+
builder.Insert(0, new string('a', 10), 1);
478+
builder.Insert(0, new string('a', 10), 1);
479+
var oldCapacity = builder.Capacity;
480+
var oldLength = builder.Length;
481+
builder.Clear();
482+
Assert.AreNotEqual(oldCapacity, builder.Capacity);
483+
Assert.AreEqual(initialCapacity, builder.Capacity);
484+
Assert.IsFalse(builder.Capacity >= 1 && builder.Capacity <= oldLength * 1.2);
485+
486+
// find max between initial capacity and 1.2 * old length
487+
int maxCapacity = initialCapacity > (int)(oldLength * 1.2) ? initialCapacity : (int)(oldLength * 1.2);
488+
489+
Assert.IsTrue(builder.Capacity >= 1 && builder.Capacity <= maxCapacity);
490+
}
491+
492+
[TestMethod]
493+
public void Clear_StringBuilderHasTwoChunks_OneChunkIsEmpty_ClearReducesCapacity()
494+
{
495+
var sb = new StringBuilder(string.Empty);
496+
int initialCapacity = sb.Capacity;
497+
for (int i = 0; i < initialCapacity; i++)
498+
{
499+
sb.Append('a');
500+
}
501+
502+
sb.Insert(0, new char[] { 'a' }, 0, 1);
503+
504+
while (sb.Length > 1)
505+
{
506+
sb.Remove(1, 1);
507+
}
508+
509+
int oldCapacity = sb.Capacity;
510+
sb.Clear();
511+
Assert.AreEqual(oldCapacity - 1, sb.Capacity);
512+
Assert.AreEqual(initialCapacity, sb.Capacity);
513+
}
446514
}
447515

448516
static class RandomExtension

0 commit comments

Comments
 (0)