cic_fixed/
decimator.rs

1//! Decimator (downsampler) for cic decimation filter.  
2
3/// Decimator
4#[derive(Default, Clone, Copy)]
5pub(crate) struct Decimator<const M: usize> {
6    counter: usize,
7}
8
9impl<const M: usize> Decimator<M> {
10    pub(crate) const fn new() -> Self {
11        Self { counter: 0 }
12    }
13
14    /// Decimate the input and return the output.
15    ///
16    /// # Arguments
17    ///
18    /// * `input` - The input to decimate.
19    ///
20    /// # Returns
21    ///
22    /// The output of the decimator.  
23    /// When the decimator is ready to output a value, it will return some(input). Otherwise, it will return None.  
24    #[inline]
25    pub(crate) fn decimate(&mut self, input: i32) -> Option<i32> {
26        self.counter += 1;
27        if self.counter == M {
28            self.counter = 0;
29            Some(input)
30        } else {
31            None
32        }
33    }
34}
35
36#[cfg(test)]
37mod tests {
38    use super::*;
39
40    #[test]
41    fn decimator_test() {
42        let mut decimator = Decimator::<4>::new();
43        let result = decimator.decimate(1);
44        assert!(result.is_none());
45        let result = decimator.decimate(2);
46        assert!(result.is_none());
47        let result = decimator.decimate(3);
48        assert!(result.is_none());
49        let result = decimator.decimate(4);
50        assert!(result.is_some());
51        assert_eq!(result.unwrap(), 4);
52
53        let result = decimator.decimate(5);
54        assert!(result.is_none());
55        let result = decimator.decimate(6);
56        assert!(result.is_none());
57        let result = decimator.decimate(7);
58        assert!(result.is_none());
59        let result = decimator.decimate(8);
60        assert!(result.is_some());
61        assert_eq!(result.unwrap(), 8);
62    }
63}