rta_for_fps_lib/window/
window_end.rs

1//! Module for the Implementation of the `WindowEnd` type (to be renamed)
2
3use core::cmp::Ordering;
4use core::iter::Sum;
5use core::ops::{Add, AddAssign, Sub};
6
7use crate::time::TimeUnit;
8
9// TODO find better name
10/// Type for the
11/// 1. End of a window
12/// 2. Length of a window
13/// 3. Capacity of a Curve
14#[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
15pub enum WindowEnd {
16    /// A Finite Window end, Window length, Curve length
17    Finite(TimeUnit),
18    /// An Infinite Window end, Window length, Curve length
19    Infinite,
20}
21
22impl WindowEnd {
23    /// return the minimal value
24    /// Finite values are always smaller than Infinite
25    #[must_use]
26    pub fn min(self, other: Self) -> Self {
27        if self < other {
28            self
29        } else {
30            other
31        }
32    }
33}
34
35impl AddAssign for WindowEnd {
36    fn add_assign(&mut self, rhs: Self) {
37        *self = *self + rhs;
38    }
39}
40
41impl Add for WindowEnd {
42    type Output = Self;
43
44    fn add(self, rhs: Self) -> Self::Output {
45        #![allow(clippy::op_ref)]
46        &self + &rhs
47    }
48}
49
50impl Add<TimeUnit> for WindowEnd {
51    type Output = WindowEnd;
52
53    fn add(self, rhs: TimeUnit) -> Self::Output {
54        match self {
55            WindowEnd::Finite(us) => Self::Finite(us + rhs),
56            WindowEnd::Infinite => Self::Infinite,
57        }
58    }
59}
60
61impl Add<WindowEnd> for TimeUnit {
62    type Output = WindowEnd;
63
64    fn add(self, rhs: WindowEnd) -> Self::Output {
65        match rhs {
66            WindowEnd::Finite(them) => WindowEnd::Finite(them + self),
67            WindowEnd::Infinite => WindowEnd::Infinite,
68        }
69    }
70}
71
72impl Add for &mut WindowEnd {
73    type Output = WindowEnd;
74
75    fn add(self, rhs: Self) -> Self::Output {
76        #![allow(clippy::op_ref)]
77        &*self + &*rhs
78    }
79}
80
81impl Add for &WindowEnd {
82    type Output = WindowEnd;
83
84    fn add(self, rhs: Self) -> Self::Output {
85        match (self, rhs) {
86            (WindowEnd::Finite(a), WindowEnd::Finite(b)) => WindowEnd::Finite(*a + *b),
87            (WindowEnd::Infinite, _) | (_, WindowEnd::Infinite) => WindowEnd::Infinite,
88        }
89    }
90}
91
92impl PartialOrd for WindowEnd {
93    fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
94        match (self, other) {
95            (Self::Infinite, Self::Infinite) => Some(Ordering::Equal),
96            (Self::Infinite, Self::Finite(_)) => Some(Ordering::Greater),
97            (Self::Finite(_), Self::Infinite) => Some(Ordering::Less),
98            (Self::Finite(a), Self::Finite(b)) => a.partial_cmp(b),
99        }
100    }
101}
102
103impl PartialEq<TimeUnit> for WindowEnd {
104    fn eq(&self, other: &TimeUnit) -> bool {
105        match self {
106            WindowEnd::Finite(us) => us.eq(other),
107            WindowEnd::Infinite => false,
108        }
109    }
110}
111
112impl PartialEq<WindowEnd> for TimeUnit {
113    fn eq(&self, other: &WindowEnd) -> bool {
114        match other {
115            WindowEnd::Finite(them) => them.eq(self),
116            WindowEnd::Infinite => false,
117        }
118    }
119}
120
121impl PartialOrd<TimeUnit> for WindowEnd {
122    fn partial_cmp(&self, other: &TimeUnit) -> Option<Ordering> {
123        match self {
124            WindowEnd::Finite(us) => us.partial_cmp(other),
125            WindowEnd::Infinite => Some(Ordering::Greater),
126        }
127    }
128}
129
130impl PartialOrd<WindowEnd> for TimeUnit {
131    fn partial_cmp(&self, other: &WindowEnd) -> Option<Ordering> {
132        match other {
133            WindowEnd::Finite(them) => self.partial_cmp(them),
134            WindowEnd::Infinite => Some(Ordering::Less),
135        }
136    }
137}
138
139impl<I: Into<TimeUnit>> From<Option<I>> for WindowEnd {
140    fn from(time: Option<I>) -> Self {
141        time.map_or(Self::Infinite, |time| Self::Finite(time.into()))
142    }
143}
144
145impl<I: Into<TimeUnit>> From<I> for WindowEnd {
146    fn from(time: I) -> Self {
147        Self::Finite(time.into())
148    }
149}
150
151impl Sum for WindowEnd {
152    fn sum<I: Iterator<Item = Self>>(iter: I) -> Self {
153        iter.fold(WindowEnd::Finite(TimeUnit::ZERO), |acc, next| {
154            match (acc, next) {
155                (Self::Finite(a), Self::Finite(b)) => Self::Finite(a + b),
156                (WindowEnd::Infinite, _) | (_, WindowEnd::Infinite) => Self::Infinite,
157            }
158        })
159    }
160}
161
162impl Sub<TimeUnit> for WindowEnd {
163    type Output = WindowEnd;
164
165    fn sub(self, rhs: TimeUnit) -> Self::Output {
166        match self {
167            WindowEnd::Finite(time) => Self::Finite(time - rhs),
168            WindowEnd::Infinite => Self::Infinite,
169        }
170    }
171}