Reuse Stopwatch instances or use Stopwatch.GetTimestamp – the code creates a new Stopwatch for every message, which allocates an object. The Stopwatch class is more precise and lightweight than DateTime.Now.
, but creating thousands of instances still incurs overhead. In hot paths, call Stopwatch.GetTimestamp() at the start and compute elapsed time using Stopwatch.GetElapsedTime to avoid allocation; or pool Stopwatch instances if precise measurement is necessary.
Cache delegates – the telemetry setup caches delegates for metrics recording, which is good. Similarly cache the input cast Func<object,T> or the key selector to avoid repeated boxing/unboxing in generic operators.
Avoid boxing in Process – currently operators take object input and cast to T. Using IOperator<T> with a generic Process(T input) avoids boxing and repeated type checks. This change would require making the pipeline generic, but will improve performance for value types.
Use List<T>.AddRange instead of iterative adds – when grouping, the code retrieves a list and calls Add on each element. If many elements are grouped at once (e.g., through FlatMap), using AddRange can reduce internal array resizing.
Reuse
Stopwatchinstances or useStopwatch.GetTimestamp– the code creates a newStopwatchfor every message, which allocates an object. The Stopwatch class is more precise and lightweight thanDateTime.Now., but creating thousands of instances still incurs overhead. In hot paths, call Stopwatch.GetTimestamp() at the start and compute elapsed time using Stopwatch.GetElapsedTime to avoid allocation; or pool Stopwatch instances if precise measurement is necessary.
Cache delegates – the telemetry setup caches delegates for metrics recording, which is good. Similarly cache the input cast Func<object,T> or the key selector to avoid repeated boxing/unboxing in generic operators.
Avoid boxing in Process – currently operators take object input and cast to T. Using
IOperator<T>with a generic Process(T input) avoids boxing and repeated type checks. This change would require making the pipeline generic, but will improve performance for value types.Use
List<T>.AddRangeinstead of iterative adds – when grouping, the code retrieves a list and calls Add on each element. If many elements are grouped at once (e.g., through FlatMap), using AddRange can reduce internal array resizing.