Struct FixedSizeValueStringBuilder
- Namespace
- LinkDotNet.StringBuilder
- Assembly
- LinkDotNet.StringBuilder.dll
A string builder backed by a fixed-size, caller-supplied buffer which never grows and never rents a replacement buffer. Formatting arbitrary custom values and converting nonempty content to a string can still allocate on the heap.
public ref struct FixedSizeValueStringBuilder
- Inherited Members
Remarks
This is a ref struct which has certain limitations. You can only store it in a local variable or another ref struct.
Unlike ValueStringBuilder, this type never rents from an array pool. Appending follows two rules:
- Every append is atomic - it either fits entirely or writes nothing at all.
- The first append that does not fit sets Overflowed, after which every further append is a no-op. The content is therefore always a valid prefix of what was intended.
Because of the second rule a later, smaller append is dropped even when it would still fit. Call
ClearOverflow() to deliberately carry on regardless.
There is no IDisposable implementation: nothing is ever rented, so there is nothing to return.
var builder = new FixedSizeValueStringBuilder(stackalloc char[32]);
builder.Append("Hello World");
var result = builder.ToString();
Constructors
FixedSizeValueStringBuilder(Span<char>)
Initializes a new instance of the FixedSizeValueStringBuilder struct.
public FixedSizeValueStringBuilder(Span<char> buffer)
Parameters
bufferSpan<char>The buffer to write into. It is never replaced or resized, so its length is the hard upper bound for the content. Typically stack-allocated via
stackalloc.
Properties
Capacity
Gets the length of the buffer this instance was created with.
public readonly int Capacity { get; }
Property Value
- int
The length of the buffer this instance was created with.
IsEmpty
Gets a value indicating whether nothing has been written yet.
public readonly bool IsEmpty { get; }
Property Value
this[int]
Returns the character at the given index.
public readonly ref char this[int index] { get; }
Parameters
indexintCharacter position to retrieve.
Property Value
Exceptions
- IndexOutOfRangeException
Thrown when
indexis negative or not smaller than Length. Only characters which were actually written are addressable, never the unwritten remainder of the buffer.
Length
Gets the number of characters written so far.
public readonly int Length { get; }
Property Value
- int
The number of characters written so far.
Overflowed
Gets a value indicating whether an append did not fit and was therefore dropped.
public readonly bool Overflowed { get; }
Property Value
- bool
true if an append was dropped; otherwise, false. Once set, every further append is a no-op until ClearOverflow() or Clear() is called.
Remaining
Gets the number of characters which still fit into the buffer.
public readonly int Remaining { get; }
Property Value
- int
The number of characters which still fit into the buffer. This can be greater than zero while Overflowed is true, in which case nothing more will be written until ClearOverflow() or Clear() is called.
Methods
Append(ref AppendInterpolatedStringHandler)
Appends an interpolated string to the builder.
public void Append(ref FixedSizeValueStringBuilder.AppendInterpolatedStringHandler handler)
Parameters
handlerFixedSizeValueStringBuilder.AppendInterpolatedStringHandlerThe interpolated string handler.
Remarks
Atomicity applies per literal and per hole, not to the interpolated string as a whole. The first part which does not fit sets Overflowed and the remaining parts are skipped, so the content stays a valid prefix of the interpolated string.
Append(bool)
Appends the string representation of a boolean. Dropped if it does not fit completely.
public void Append(bool value)
Parameters
valueboolBool value to add.
Append(char)
Appends a single character. Dropped if the buffer has no room left.
public void Append(char value)
Parameters
valuecharCharacter to add.
Append(scoped ReadOnlySpan<char>)
Appends a string. Dropped if it does not fit completely.
public void Append(scoped ReadOnlySpan<char> str)
Parameters
strReadOnlySpan<char>String to be added to this builder.
Append(string?)
Appends a string. Dropped if it does not fit completely.
public void Append(string? value)
Parameters
valuestringThe string to be added to this builder.
Append(Rune)
Appends a single rune. Dropped if it does not fit completely, so a surrogate pair is never split.
public void Append(Rune value)
Parameters
valueRuneRune to add.
AppendLine()
Appends NewLine. Dropped if it does not fit completely.
public void AppendLine()
AppendLine(ref AppendInterpolatedStringHandler)
Appends an interpolated string followed by NewLine to the builder.
public void AppendLine(ref FixedSizeValueStringBuilder.AppendInterpolatedStringHandler handler)
Parameters
handlerFixedSizeValueStringBuilder.AppendInterpolatedStringHandlerThe interpolated string handler.
Remarks
Atomicity applies per literal and per hole, not to the interpolated string as a whole. The first part which does not fit sets Overflowed and the remaining parts - including the new line - are skipped.
AppendLine(scoped ReadOnlySpan<char>)
Appends a string followed by NewLine. Both are dropped together unless both fit.
public void AppendLine(scoped ReadOnlySpan<char> str)
Parameters
strReadOnlySpan<char>String to be added to this builder.
AppendLine(string?)
Appends a string followed by NewLine. Both are dropped together unless both fit.
public void AppendLine(string? value)
Parameters
valuestringThe string to be added to this builder.
Append<T>(T, scoped ReadOnlySpan<char>, IFormatProvider?)
Appends the string representation of the value. Dropped if it does not fit completely, so a formatted value is never written out half-way.
public void Append<T>(T value, scoped ReadOnlySpan<char> format = default, IFormatProvider? formatProvider = null) where T : ISpanFormattable
Parameters
valueTFormattable span to add.
formatReadOnlySpan<char>Optional formatter. If not provided the default of the given instance is taken.
formatProviderIFormatProviderOptional format provider.
Type Parameters
TAny ISpanFormattable.
AsSpan()
Returns the written content as a ReadOnlySpan<T>.
public readonly ReadOnlySpan<char> AsSpan()
Returns
- ReadOnlySpan<char>
The written content as a ReadOnlySpan<T>.
Clear()
Discards the written content and resets Overflowed so the buffer can be reused.
public void Clear()
ClearOverflow()
Resets Overflowed while keeping the written content, so appending continues into whatever room is left.
public void ClearOverflow()
Remarks
Read Overflowed before calling this if you need to know whether anything was actually dropped.
MoveToValueStringBuilder()
Hands the buffer and its content over to a ValueStringBuilder which can grow beyond the fixed capacity, and consumes this instance.
public ValueStringBuilder MoveToValueStringBuilder()
Returns
- ValueStringBuilder
A ValueStringBuilder continuing where this instance left off. Nothing is copied and nothing is rented, so the move itself never allocates. Dispose the result as usual.
Remarks
Both builders would otherwise write into the same memory, so this instance is left consumed: an empty builder with zero capacity whose Overflowed is true. Reading it is safe, and any further append is a no-op rather than a write into a buffer somebody else now owns.
Consuming this instance can only neutralize this one variable. The caller must own the buffer uniquely at the point of the move: neither the Span<T> passed to the constructor nor any struct copy taken before the move may be written to afterwards. Both still alias the same memory and would corrupt the content of the returned ValueStringBuilder - the compiler cannot detect it, so the discipline is yours.
Exceptions
- InvalidOperationException
Overflowed is true. The content is an incomplete prefix and ValueStringBuilder has nowhere to carry that information. Call ClearOverflow() first if the truncation was intended.
ToString()
Creates a string instance from the written content.
public override readonly string ToString()
Returns
TryCopyTo(Span<char>)
Tries to copy the written content into the given Span<T>.
public readonly bool TryCopyTo(Span<char> destination)