An analyzer takes some data as an input, and returns an analyzed output. Analyzers should not contain any state. They must define whether they can run on a multithreaded executor, and provide a means of analyzing input data to return some form of result.
A factory to create analyzers.
A loop to execute repeated analysis. The loop uses coroutines to run the Analyzer.analyze method. If the Analyzer is threadsafe, multiple coroutines will be used. If not, a single coroutine will be used.
A pool of analyzers.
This kind of AnalyzerLoop will process data provided as part of its constructor. Data will be processed in the order provided.
This kind of AnalyzerLoop will process data until the result handler indicates that it has reached a terminal state and is no longer listening.
The ResultAggregator processes results from analyzers until a condition is met. That condition is part of the aggregator's logic.
Keep track of a single stat's duration and result
A specialized result handler that has some form of state.
A result handler with a method that notifies when all data has been processed.