pub struct Anomaly<const N: usize> { /* private fields */ }Expand description
Flags a reading that lies far from the recent norm.
“Tell me when something is off” needs a baseline: a reading is suspicious only relative to
what is usual. An Anomaly keeps a rolling window of recent readings and flags one that
sits more than a chosen number of standard deviations from their mean - the three-sigma
rule, the standard z-score test, with the threshold left to the caller (3.0 is the
usual choice). It is dependency-free: instead of taking a square root it compares the
squared deviation against the squared threshold, which is the same test.
With a perfectly flat baseline the spread is zero, so any change at all reads as anomalous; real sensor noise gives a non-zero baseline, where this is not an issue.
A reading that is not a finite number, such as the NaN a failed sensor reports, is always flagged, and is kept out of the baseline so it cannot blind the detector to the readings after it.
§Examples
use pamoja_kit::Anomaly;
let mut watch = Anomaly::<8>::new(3.0);
// Establish a steady baseline.
for reading in [10.0, 10.2, 9.8, 10.1, 9.9, 10.0, 10.2, 9.8] {
watch.check(reading);
}
assert!(!watch.check(10.1)); // close to the norm: fine
assert!(watch.check(20.0)); // a far jump: flaggedImplementations§
Source§impl<const N: usize> Anomaly<N>
impl<const N: usize> Anomaly<N>
Sourcepub fn new(sigmas: f32) -> Self
pub fn new(sigmas: f32) -> Self
Creates a detector that flags readings beyond sigmas standard deviations.
§Arguments
sigmas- the threshold in standard deviations;3.0is the common three-sigma rule. Its magnitude is used, and one that is not a number is taken as zero, so the mistake shows as alarms rather than as silence.
§Returns
A detector with an empty history.
Sourcepub fn with_capacity(sigmas: f32, capacity: usize) -> Self
pub fn with_capacity(sigmas: f32, capacity: usize) -> Self
Sourcepub fn check(&mut self, reading: f32) -> bool
pub fn check(&mut self, reading: f32) -> bool
Tests a reading against the recent norm, then folds it into the history.
The reading is judged against the window of earlier readings, so the value being tested does not inflate its own baseline. Until at least two readings have been seen there is no spread to judge against, so nothing is flagged: from the third reading on, a reading can be. A reading that is not a finite number is always flagged and is not kept.
§Arguments
reading- the latest reading.
§Returns
true if reading lies more than the configured standard deviations from the mean
of the recent window.
Sourcepub fn capacity(&self) -> usize
pub fn capacity(&self) -> usize
Returns the most readings the baseline keeps: N, or less when made with
with_capacity.