interval/
interval.rs

1// Copyright 2015 Pierre Talbot (IRCAM)
2
3// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
4// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
5// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
6// option. This file may not be copied, modified, or distributed
7// except according to those terms.
8
9//! Closed and bounded generic interval.
10//!
11//! Let `D` be an ordered set and `{i,j} ∈ D`. The interval `I` whose bounds are `{i,j}` is defined as `I = {x ∈ D | i <= x <= j}` and is denoted as `[i..j]`. Only interval with bound types implementing `Num` and `Width` is currently available.
12//!
13//! Most of the operations in `gcollections::ops::*` are implemented. Intervals specific operations, proposed in `ops::*`, are also implemented. There is no `union` operation since this interval representation is not precise enough, and so an union could be over-approximated. For example, consider `[1..2] U [5..6]`, the only possible representation is `[1..6]` which is not exact by the definition of union of sets. However, this operation exists and is named `hull`.
14//!
15//! # Examples
16//!
17//! ```rust
18//! use crate::interval::Interval;
19//! use crate::interval::ops::*;
20//! use gcollections::ops::*;
21//!
22//! # fn main() {
23//! let a = Interval::new(0, 5);
24//! let b = Interval::singleton(10);
25//!
26//! let c = a.hull(&b);
27//! let d = c.difference(&a);
28//!
29//! assert_eq!(c, Interval::new(0,10));
30//! assert_eq!(d, Interval::new(6,10));
31//! # }
32//! ```
33//!
34//! # See also
35//! [interval set](../interval_set/index.html).
36
37use crate::ops::*;
38use gcollections::ops::*;
39use gcollections::*;
40use serde::de::{self, SeqAccess, Visitor};
41use serde::ser::SerializeTuple;
42use serde::{Deserialize, Deserializer, Serialize, Serializer};
43use trilean::SKleene;
44
45use num_traits::{Num, Zero};
46use std::cmp::{max, min};
47use std::fmt::{self, Display, Error, Formatter};
48use std::marker::PhantomData;
49use std::ops::{Add, Mul, RangeFrom, RangeInclusive, RangeToInclusive, Sub};
50
51/// Closed interval (endpoints included).
52#[derive(Debug, Copy, Clone)]
53pub struct Interval<Bound> {
54    lb: Bound,
55    ub: Bound,
56}
57
58impl<Bound> Serialize for Interval<Bound>
59where
60    Bound: Serialize + Width + Num,
61{
62    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
63    where
64        S: Serializer,
65    {
66        if self.is_empty() {
67            serializer.serialize_none()
68        } else {
69            let mut tuple = serializer.serialize_tuple(2)?;
70            tuple.serialize_element(&self.lb)?;
71            tuple.serialize_element(&self.ub)?;
72            tuple.end()
73        }
74    }
75}
76
77impl<'de, Bound> Deserialize<'de> for Interval<Bound>
78where
79    Bound: Width + Num + Deserialize<'de>,
80{
81    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
82    where
83        D: Deserializer<'de>,
84    {
85        struct IntervalVisitor<Bound> {
86            marker: PhantomData<fn() -> Bound>,
87        }
88        impl<Bound> IntervalVisitor<Bound> {
89            fn new() -> Self {
90                IntervalVisitor {
91                    marker: PhantomData,
92                }
93            }
94        }
95        impl<'de, Bound> Visitor<'de> for IntervalVisitor<Bound>
96        where
97            Bound: Width + Deserialize<'de> + Num,
98        {
99            type Value = Interval<Bound>;
100
101            fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
102                formatter.write_str("tuple of two numbers or none")
103            }
104
105            fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
106            where
107                A: SeqAccess<'de>,
108            {
109                let lower = seq
110                    .next_element::<Bound>()?
111                    .ok_or_else(|| de::Error::invalid_length(0, &self))?;
112                let upper = seq
113                    .next_element::<Bound>()?
114                    .ok_or_else(|| de::Error::invalid_length(1, &self))?;
115                let mut extra_elements = 0;
116                while seq.next_element::<de::IgnoredAny>()?.is_some() {
117                    extra_elements += 1;
118                }
119                if extra_elements > 0 {
120                    return Err(de::Error::invalid_length(2 + extra_elements, &self));
121                }
122                Ok(Interval::new(lower, upper))
123            }
124
125            fn visit_none<E>(self) -> Result<Self::Value, E>
126            where
127                E: de::Error,
128            {
129                Ok(Interval::<Bound>::empty())
130            }
131        }
132        deserializer.deserialize_any(IntervalVisitor::new())
133    }
134}
135
136impl<Bound> IntervalKind for Interval<Bound> {}
137
138impl<Bound> Collection for Interval<Bound> {
139    type Item = Bound;
140}
141
142impl<Bound> Interval<Bound>
143where
144    Bound: Width + Num,
145{
146    fn into_optional(self) -> Optional<Bound> {
147        if self.is_empty() {
148            Optional::empty()
149        } else if self.is_singleton() {
150            Optional::singleton(self.lb)
151        } else {
152            panic!("Only empty interval or singleton can be transformed into an option.");
153        }
154    }
155}
156
157impl<Bound: Width + Num> Eq for Interval<Bound> {}
158
159impl<Bound> PartialEq<Interval<Bound>> for Interval<Bound>
160where
161    Bound: Width + Num,
162{
163    /// Checks whether two intervals are equal.
164    /// The bounds must be the same.
165    /// ```
166    /// # use interval::prelude::*;
167    /// assert_eq!(Interval::new(8, 24), Interval::new(8, 24));
168    /// assert_ne!(Interval::new(6, 9), Interval::new(6, 10));
169    /// ```
170    /// Any pair of empty intervals are equal to each other but no other interval.
171    /// ```
172    /// # use interval::prelude::*;
173    /// assert_eq!(Interval::<usize>::empty(), Interval::<usize>::empty());
174    /// assert_ne!(Interval::new(0, 1), Interval::empty());
175    /// assert_ne!(Interval::empty(), Interval::singleton(11));
176    /// ```
177    fn eq(&self, other: &Interval<Bound>) -> bool {
178        if self.is_empty() && other.is_empty() {
179            true
180        } else {
181            self.lb == other.lb && self.ub == other.ub
182        }
183    }
184}
185
186impl<Bound> Interval<Bound>
187where
188    Bound: Clone,
189{
190    fn low(&self) -> Bound {
191        self.lb.clone()
192    }
193    fn up(&self) -> Bound {
194        self.ub.clone()
195    }
196}
197
198impl<Bound> Interval<Bound>
199where
200    Bound: Width + Num,
201{
202    fn min_lb(ub: Bound) -> Interval<Bound> {
203        Interval::new(<Bound as Width>::min_value(), ub)
204    }
205
206    fn max_ub(lb: Bound) -> Interval<Bound> {
207        Interval::new(lb, <Bound as Width>::max_value())
208    }
209}
210
211impl<Bound> Range for Interval<Bound>
212where
213    Bound: Width,
214{
215    /// Constructs an interval with the lower and upper bound (inclusive).
216    /// ```
217    /// # use interval::prelude::*;
218    /// let interval = Interval::new(3, 8);
219    /// assert_eq!(interval.lower(), 3);
220    /// assert_eq!(interval.upper(), 8);
221    /// assert!(interval.contains(&3));
222    /// assert!(!interval.contains(&2));
223    /// assert!(interval.contains(&8));
224    /// assert!(!interval.contains(&9));
225    /// assert!(!interval.is_empty());
226    /// ```
227    /// For intervals containing a single value, the [`Interval::singleton`] constructor is preferred.
228    /// ```
229    /// # use interval::prelude::*;
230    /// assert_eq!(Interval::new(6, 6), Interval::singleton(6));
231    /// ```
232    /// For an empty interval, use the [`Interval::empty`] constructor.
233    ///
234    /// The bounds of the constructor are bounded by [`Interval::whole`].
235    /// This means that not all possible intervals can be constructed.
236    /// ```should_panic
237    /// # use interval::prelude::*;
238    /// Interval::<u8>::new(0, 255); // panics!
239    /// Interval::<u8>::new(0, 254); // constructs normally
240    ///
241    /// Interval::<i8>::new(-128, 127); // panics!
242    /// Interval::<i8>::new(-127, 127); // constructs normally
243    /// ```
244    fn new(lb: Bound, ub: Bound) -> Interval<Bound> {
245        debug_assert!(
246            lb >= <Bound as Width>::min_value(),
247            "Lower bound exceeds the minimum value of a bound."
248        );
249        debug_assert!(
250            ub <= <Bound as Width>::max_value(),
251            "Upper bound exceeds the maximum value of a bound."
252        );
253        Interval { lb, ub }
254    }
255}
256
257impl<Bound> Bounded for Interval<Bound>
258where
259    Bound: Num + Width + Clone,
260{
261    /// Returns the lower bound of an interval.
262    /// ```
263    /// # use interval::prelude::*;
264    /// assert_eq!(Interval::new(8, 20).lower(), 8);
265    /// assert_eq!(Interval::singleton(4).lower(), 4);
266    /// ```
267    /// However, this will panic on an empty interval.
268    /// ```should_panic
269    /// # use interval::prelude::*;
270    /// Interval::<u8>::empty().lower(); // panics!
271    /// ```
272    fn lower(&self) -> Bound {
273        debug_assert!(
274            !self.is_empty(),
275            "Cannot access lower bound on empty interval."
276        );
277        self.low()
278    }
279
280    /// Returns the upper bound of an interval.
281    /// ```
282    /// # use interval::prelude::*;
283    /// assert_eq!(Interval::new(8, 20).upper(), 20);
284    /// assert_eq!(Interval::singleton(4).upper(), 4);
285    /// ```
286    /// However, this will panic on an empty interval.
287    /// ```should_panic
288    /// # use interval::prelude::*;
289    /// Interval::<u8>::empty().upper(); // panics!
290    /// ```
291    fn upper(&self) -> Bound {
292        debug_assert!(
293            !self.is_empty(),
294            "Cannot access upper bound on empty interval."
295        );
296        self.up()
297    }
298}
299
300impl<Bound> Singleton for Interval<Bound>
301where
302    Bound: Width + Clone,
303{
304    /// Constructs an interval containing a single value - the lower and upper bounds are the same.
305    /// ```
306    /// # use interval::prelude::*;
307    /// let interval_5 = Interval::singleton(5);
308    /// assert_eq!(interval_5.size(), 1 as u32);
309    /// assert_eq!(interval_5.lower(), interval_5.upper());
310    /// assert!(interval_5.contains(&5));
311    /// assert!(!interval_5.is_empty());
312    /// ```
313    fn singleton(x: Bound) -> Interval<Bound> {
314        Interval::new(x.clone(), x)
315    }
316}
317
318impl<Bound> Empty for Interval<Bound>
319where
320    Bound: Width + Num,
321{
322    /// Constructs an empty interval.
323    /// The type needs to be specified or inferred as `Interval` is parametrized by its input.
324    /// ```
325    /// # use interval::prelude::*;
326    /// assert_eq!(Interval::<i32>::empty().size(), 0);
327    /// assert_eq!(Interval::<u32>::empty().size(), 0);
328    /// assert!(Interval::<u16>::empty().is_empty());
329    /// ```
330    fn empty() -> Interval<Bound> {
331        Interval::new(Bound::one(), Bound::zero())
332    }
333}
334
335impl<Bound> Whole for Interval<Bound>
336where
337    Bound: Width + Num,
338{
339    /// Calculates the maximum range of an interval.
340    ///
341    /// For an unsigned integer, this sets the minimum of the interval to the minimum of the type (e.g. `u32::min_value()`)
342    /// and the maximum to one less than the maximum value (e.ge `u32::max_value() - 1`).
343    ///
344    /// For a signed integer, this sets the minimum of the interval to one more than the minimum of the type (e.g. `i32::min_value() + 1`)
345    /// and the maximum to than the maximum value (e.ge `i32::max_value()`).
346    /// This ensures that it is always possible to calculate the width without overflow (using the same number of bits).
347    /// ```
348    /// # use interval::prelude::*;
349    /// // u8: 0 <-> 255
350    /// assert_eq!(Interval::<u8>::whole(), Interval::new(0, 254));
351    /// // i8: -128 <-> 127
352    /// assert_eq!(Interval::<i8>::whole(), Interval::new(-127, 127));
353    /// assert_eq!(Interval::<usize>::whole(), Interval::new(usize::min_value(), usize::max_value() - 1));
354    /// assert_eq!(Interval::<isize>::whole(), Interval::new(isize::min_value() + 1, isize::max_value()));
355    /// ```
356    fn whole() -> Interval<Bound> {
357        Interval::new(<Bound as Width>::min_value(), <Bound as Width>::max_value())
358    }
359}
360
361/// `IsSingleton` and `IsEmpty` are defined automatically in `gcollections`.
362impl<Bound> Cardinality for Interval<Bound>
363where
364    Bound: Width + Num,
365{
366    type Size = <Bound as Width>::Output;
367
368    /// Calculates the size of an interval (the number of integers it contains).
369    /// This includes both endpoints.
370    /// The size of the interval is unsigned, but has the same number of bits as the interval bounds.
371    /// ```
372    /// # use interval::prelude::*;
373    /// assert_eq!(Interval::<i32>::new(1, 10).size(), 10 as u32);
374    /// assert_eq!(Interval::<usize>::new(1, 10).size(), 10 as usize);
375    /// // Default is to use i32.
376    /// assert_eq!(Interval::singleton(5).size(), 1 as u32);
377    /// assert_eq!(Interval::<i64>::empty().size(), 0);
378    /// // Doesn't overflow:
379    /// assert_eq!(Interval::<usize>::whole().size(), usize::max_value());
380    /// ```
381    fn size(&self) -> <Bound as Width>::Output {
382        if self.lb > self.ub {
383            <<Bound as Width>::Output>::zero()
384        } else {
385            Bound::width(&self.lb, &self.ub)
386        }
387    }
388}
389
390impl<Bound> Disjoint for Interval<Bound>
391where
392    Bound: Width + Num,
393{
394    /// Calculates whether two intervals do *not* overlap.
395    /// ```
396    /// # use interval::prelude::*;
397    /// assert_eq!(Interval::new(8, 9).is_disjoint(&Interval::new(1, 2)), true);
398    /// assert_eq!(Interval::new(1, 5).is_disjoint(&Interval::new(3, 4)), false);
399    /// assert_eq!(Interval::new(3, 5).is_disjoint(&Interval::new(5, 7)), false);
400    /// assert_eq!(Interval::new(3, 3).is_disjoint(&Interval::new(3, 3)), false);
401    /// assert_eq!(Interval::empty().is_disjoint(&Interval::new(2, 3)), true);
402    /// assert_eq!(Interval::new(4, 6).is_disjoint(&Interval::empty()), true);
403    /// assert_eq!(Interval::<usize>::empty().is_disjoint(&Interval::empty()), true);
404    /// ```
405    fn is_disjoint(&self, other: &Interval<Bound>) -> bool {
406        self.is_empty() || other.is_empty() || self.lb > other.ub || other.lb > self.ub
407    }
408}
409
410impl<Bound> Disjoint<Bound> for Interval<Bound>
411where
412    Bound: Num + Ord,
413{
414    /// Calculates whether a value is excluded from an interval.
415    /// ```
416    /// # use interval::prelude::*;
417    /// assert_eq!(Interval::new(8, 9).is_disjoint(&1), true);
418    /// assert_eq!(Interval::new(1, 5).is_disjoint(&3), false);
419    /// assert_eq!(Interval::new(3, 5).is_disjoint(&5), false);
420    /// assert_eq!(Interval::new(3, 3).is_disjoint(&3), false);
421    /// assert_eq!(Interval::empty().is_disjoint(&6), true);
422    /// ```
423    fn is_disjoint(&self, value: &Bound) -> bool {
424        !self.contains(value)
425    }
426}
427
428macro_rules! primitive_interval_disjoint
429{
430  ( $( $source:ty ),* ) =>
431  {$(
432    impl Disjoint<Interval<$source>> for $source
433    {
434      #[doc = concat!(
435        r#"
436        Calculates whether a value is excluded from an interval.
437        ```
438        # use interval::prelude::*;
439        assert_eq!((1 as "#, stringify!($source), r#").is_disjoint(&Interval::new(8, 9)), true);
440        assert_eq!((3 as "#, stringify!($source), r#").is_disjoint(&Interval::new(1, 5)), false);
441        assert_eq!((5 as "#, stringify!($source), r#").is_disjoint(&Interval::new(3, 5)), false);
442        assert_eq!((3 as "#, stringify!($source), r#").is_disjoint(&Interval::new(3, 3)), false);
443        assert_eq!((6 as "#, stringify!($source), r#").is_disjoint(&Interval::empty()), true);
444        ```
445        "#
446      )]
447      fn is_disjoint(&self, value: &Interval<$source>) -> bool {
448        value.is_disjoint(self)
449      }
450    }
451  )*}
452}
453
454primitive_interval_disjoint!(i8, u8, i16, u16, i32, u32, i64, u64, isize, usize);
455
456impl<Bound> Disjoint<Optional<Bound>> for Interval<Bound>
457where
458    Bound: Num + Ord,
459{
460    /// Calculates whether an optional is excluded from an interval.
461    /// ```
462    /// # use interval::prelude::*;
463    /// assert_eq!(Interval::new(8, 9).is_disjoint(&Optional::singleton(1)), true);
464    /// assert_eq!(Interval::new(1, 5).is_disjoint(&Optional::singleton(3)), false);
465    /// assert_eq!(Interval::new(3, 5).is_disjoint(&Optional::singleton(5)), false);
466    /// assert_eq!(Interval::new(3, 3).is_disjoint(&Optional::singleton(3)), false);
467    /// assert_eq!(Interval::<usize>::empty().is_disjoint(&Optional::singleton(6)), true);
468    /// assert_eq!(Interval::new(4, 7).is_disjoint(&Optional::empty()), true);
469    /// assert_eq!(Interval::<isize>::empty().is_disjoint(&Optional::empty()), true);
470    /// ```
471    fn is_disjoint(&self, value: &Optional<Bound>) -> bool {
472        value.as_ref().map_or(true, |x| self.is_disjoint(x))
473    }
474}
475
476macro_rules! optional_interval_disjoint
477{
478  ( $( $source:ty ),* ) =>
479  {$(
480    impl Disjoint<Interval<$source>> for Optional<$source>
481    {
482      #[doc = concat!(
483        r#"
484        Calculates whether an optional is excluded from an interval.
485        ```
486        # use interval::prelude::*;
487        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(1).is_disjoint(&Interval::new(8, 9)), true);
488        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(3).is_disjoint(&Interval::new(1, 5)), false);
489        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(5).is_disjoint(&Interval::new(3, 5)), false);
490        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(3).is_disjoint(&Interval::new(3, 3)), false);
491        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(6).is_disjoint(&Interval::empty()), true);
492        assert_eq!(Optional::<"#, stringify!($source), r#">::empty().is_disjoint(&Interval::new(4, 7)), true);
493        assert_eq!(Optional::<"#, stringify!($source), r#">::empty().is_disjoint(&Interval::empty()), true);
494        ```
495        "#
496      )]
497      fn is_disjoint(&self, value: &Interval<$source>) -> bool {
498        value.is_disjoint(self)
499      }
500    }
501  )*}
502}
503
504optional_interval_disjoint!(i8, u8, i16, u16, i32, u32, i64, u64, isize, usize);
505
506impl<Bound> Overlap for Interval<Bound>
507where
508    Bound: Width + Num,
509{
510    /// Calculates whether two intervals overlap.
511    /// ```
512    /// # use interval::prelude::*;
513    /// assert_eq!(Interval::new(8, 9).overlap(&Interval::new(1, 2)), false);
514    /// assert_eq!(Interval::new(1, 5).overlap(&Interval::new(3, 4)), true);
515    /// assert_eq!(Interval::new(3, 5).overlap(&Interval::new(5, 7)), true);
516    /// assert_eq!(Interval::new(3, 3).overlap(&Interval::new(3, 3)), true);
517    /// assert_eq!(Interval::empty().overlap(&Interval::new(2, 3)), false);
518    /// assert_eq!(Interval::new(4, 6).overlap(&Interval::empty()), false);
519    /// assert_eq!(Interval::<usize>::empty().overlap(&Interval::empty()), false);
520    /// ```
521    fn overlap(&self, other: &Interval<Bound>) -> bool {
522        !self.is_disjoint(other)
523    }
524}
525
526impl<Bound> Overlap<Bound> for Interval<Bound>
527where
528    Bound: Width + Num,
529{
530    /// Calculates whether a value is included in an interval.
531    /// ```
532    /// # use interval::prelude::*;
533    /// assert_eq!(Interval::new(8, 9).overlap(&1), false);
534    /// assert_eq!(Interval::new(1, 5).overlap(&3), true);
535    /// assert_eq!(Interval::new(3, 5).overlap(&5), true);
536    /// assert_eq!(Interval::new(3, 3).overlap(&3), true);
537    /// assert_eq!(Interval::empty().overlap(&6), false);
538    /// ```
539    fn overlap(&self, other: &Bound) -> bool {
540        !self.is_disjoint(other)
541    }
542}
543
544impl<Bound> Overlap<Optional<Bound>> for Interval<Bound>
545where
546    Bound: Width + Num,
547{
548    /// Calculates whether an optional is included from an interval.
549    /// ```
550    /// # use interval::prelude::*;
551    /// assert_eq!(Interval::new(8, 9).overlap(&Optional::singleton(1)), false);
552    /// assert_eq!(Interval::new(1, 5).overlap(&Optional::singleton(3)), true);
553    /// assert_eq!(Interval::new(3, 5).overlap(&Optional::singleton(5)), true);
554    /// assert_eq!(Interval::new(3, 3).overlap(&Optional::singleton(3)), true);
555    /// assert_eq!(Interval::<usize>::empty().overlap(&Optional::singleton(6)), false);
556    /// assert_eq!(Interval::new(4, 7).overlap(&Optional::empty()), false);
557    /// assert_eq!(Interval::<isize>::empty().overlap(&Optional::empty()), false);
558    /// ```
559    fn overlap(&self, other: &Optional<Bound>) -> bool {
560        !self.is_disjoint(other)
561    }
562}
563
564macro_rules! primitive_interval_overlap
565{
566  ( $( $source:ty ),* ) =>
567  {$(
568    impl Overlap<Interval<$source>> for $source
569    {
570      #[doc = concat!(
571        r#"
572        Calculates whether a value is included in an interval.
573        ```
574        # use interval::prelude::*;
575        assert_eq!((1 as "#, stringify!($source), r#").overlap(&Interval::new(8, 9)), false);
576        assert_eq!((3 as "#, stringify!($source), r#").overlap(&Interval::new(1, 5)), true);
577        assert_eq!((5 as "#, stringify!($source), r#").overlap(&Interval::new(3, 5)), true);
578        assert_eq!((3 as "#, stringify!($source), r#").overlap(&Interval::new(3, 3)), true);
579        assert_eq!((6 as "#, stringify!($source), r#").overlap(&Interval::empty()), false);
580        ```
581        "#
582      )]
583      fn overlap(&self, other: &Interval<$source>) -> bool {
584        !self.is_disjoint(other)
585      }
586    }
587  )*}
588}
589
590primitive_interval_overlap!(i8, u8, i16, u16, i32, u32, i64, u64, isize, usize);
591
592macro_rules! optional_interval_overlap
593{
594  ( $( $source:ty ),* ) =>
595  {$(
596    impl Overlap<Interval<$source>> for Optional<$source>
597    {
598      #[doc = concat!(
599        r#"
600        Calculates whether an optional is included in an interval.
601        ```
602        # use interval::prelude::*;
603        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(1).overlap(&Interval::new(8, 9)), false);
604        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(3).overlap(&Interval::new(1, 5)), true);
605        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(5).overlap(&Interval::new(3, 5)), true);
606        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(3).overlap(&Interval::new(3, 3)), true);
607        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(6).overlap(&Interval::empty()), false);
608        assert_eq!(Optional::<"#, stringify!($source), r#">::empty().overlap(&Interval::new(4, 7)), false);
609        assert_eq!(Optional::<"#, stringify!($source), r#">::empty().overlap(&Interval::empty()), false);
610        ```
611        "#
612      )]
613      fn overlap(&self, other: &Interval<$source>) -> bool {
614        !self.is_disjoint(other)
615      }
616    }
617  )*}
618}
619
620optional_interval_overlap!(i8, u8, i16, u16, i32, u32, i64, u64, isize, usize);
621
622impl<Bound> Hull for Interval<Bound>
623where
624    Bound: Width + Num,
625{
626    type Output = Interval<Bound>;
627
628    /// Calculates the smallest interval containing two intervals.
629    /// ```
630    /// # use interval::prelude::*;
631    /// assert_eq!(Interval::hull(&Interval::new(1, 3), &Interval::new(5, 8)), Interval::new(1, 8));
632    /// assert_eq!(Interval::new(1, 3).hull(&Interval::new(5, 8)), Interval::new(1, 8));
633    /// assert_eq!(Interval::new(1, 6).hull(&Interval::new(4, 7)), Interval::new(1, 7));
634    /// assert_eq!(Interval::new(3, 9).hull(&Interval::new(5, 6)), Interval::new(3, 9));
635    /// assert_eq!(Interval::new(1, 3).hull(&Interval::empty()), Interval::new(1, 3));
636    /// assert_eq!(Interval::<usize>::empty().hull(&Interval::empty()), Interval::empty());
637    /// ```
638    fn hull(&self, other: &Interval<Bound>) -> Interval<Bound> {
639        if self.is_empty() {
640            other.clone()
641        } else if other.is_empty() {
642            self.clone()
643        } else {
644            Interval::new(min(self.low(), other.low()), max(self.up(), other.up()))
645        }
646    }
647}
648
649impl<Bound> Hull<Bound> for Interval<Bound>
650where
651    Bound: Width + Num,
652{
653    type Output = Interval<Bound>;
654
655    /// Calculates the smallest interval containing an interval and a value.
656    /// ```
657    /// # use interval::prelude::*;
658    /// assert_eq!(Interval::new(5, 8).hull(&3), Interval::new(3, 8));
659    /// assert_eq!(Interval::new(1, 3).hull(&2), Interval::new(1, 3));
660    /// assert_eq!(Interval::new(2, 6).hull(&9), Interval::new(2, 9));
661    /// assert_eq!(Interval::singleton(4).hull(&4), Interval::singleton(4));
662    /// assert_eq!(Interval::empty().hull(&5), Interval::singleton(5));
663    /// ```
664    fn hull(&self, other: &Bound) -> Interval<Bound> {
665        self.hull(&Interval::singleton(other.clone()))
666    }
667}
668
669macro_rules! primitive_interval_hull
670{
671  ( $( $source:ty ),* ) =>
672  {$(
673    impl Hull<Interval<$source>> for $source
674    {
675      type Output = Interval<$source>;
676
677      #[doc = concat!(
678        r#"
679        Calculates the smallest interval containing an interval and a value.
680        ```
681        # use interval::prelude::*;
682        assert_eq!((3 as "#, stringify!($source), r#").hull(&Interval::new(5, 8)), Interval::new(3, 8));
683        assert_eq!((2 as "#, stringify!($source), r#").hull(&Interval::new(1, 3)), Interval::new(1, 3));
684        assert_eq!((9 as "#, stringify!($source), r#").hull(&Interval::new(2, 6)), Interval::new(2, 9));
685        assert_eq!((4 as "#, stringify!($source), r#").hull(&Interval::singleton(4)), Interval::singleton(4));
686        assert_eq!((5 as "#, stringify!($source), r#").hull(&Interval::empty()), Interval::singleton(5));
687        ```
688        "#
689      )]
690      fn hull(&self, other: &Interval<$source>) -> Interval<$source> {
691        other.hull(self)
692      }
693    }
694  )*}
695}
696
697primitive_interval_hull!(i8, u8, i16, u16, i32, u32, i64, u64, isize, usize);
698
699impl<Bound> Contains for Interval<Bound>
700where
701    Bound: Ord,
702{
703    /// Calculates whether an interval contains a value.
704    /// ```
705    /// # use interval::prelude::*;
706    /// let interval = Interval::new(1, 4);
707    /// assert!(interval.contains(&1));
708    /// assert!(interval.contains(&2));
709    /// assert!(interval.contains(&3));
710    /// assert!(interval.contains(&4));
711    ///
712    /// assert!(!interval.contains(&0));
713    /// assert!(!interval.contains(&5));
714    /// ```
715    /// The empty interval contains nothing.
716    /// ```
717    /// # use interval::prelude::*;
718    /// let empty = Interval::empty();
719    /// assert!(!empty.contains(&-3));
720    /// assert!(!empty.contains(&5));
721    /// ```
722    fn contains(&self, value: &Bound) -> bool {
723        value >= &self.lb && value <= &self.ub
724    }
725}
726
727impl<Bound> Subset for Interval<Bound>
728where
729    Bound: Width + Num,
730{
731    /// Calculates whether one interval is contained in another.
732    /// The empty interval is a subset of everything.
733    /// ```
734    /// # use interval::prelude::*;
735    /// assert_eq!(Interval::new(1, 4).is_subset(&Interval::new(2, 6)), false);
736    /// assert_eq!(Interval::new(6, 7).is_subset(&Interval::new(3, 7)), true);
737    /// assert_eq!(Interval::new(8, 9).is_subset(&Interval::new(1, 2)), false);
738    /// assert_eq!(Interval::new(3, 6).is_subset(&Interval::new(4, 5)), false);
739    /// assert_eq!(Interval::new(5, 8).is_subset(&Interval::new(5, 8)), true);
740    ///
741    /// assert_eq!(Interval::empty().is_subset(&Interval::new(5, 8)), true);
742    /// assert_eq!(Interval::<usize>::empty().is_subset(&Interval::empty()), true);
743    /// ```
744    fn is_subset(&self, other: &Interval<Bound>) -> bool {
745        if self.is_empty() {
746            true
747        } else {
748            self.lb >= other.lb && self.ub <= other.ub
749        }
750    }
751}
752
753impl<Bound> ProperSubset for Interval<Bound>
754where
755    Bound: Width + Num,
756{
757    /// Calculates whether one interval is contained in another,
758    /// but they are not equal.
759    /// The empty interval is a proper subset of everything, except itself.
760    /// ```
761    /// # use interval::prelude::*;
762    /// assert_eq!(Interval::new(1, 4).is_proper_subset(&Interval::new(2, 6)), false);
763    /// assert_eq!(Interval::new(6, 7).is_proper_subset(&Interval::new(3, 7)), true);
764    /// assert_eq!(Interval::new(8, 9).is_proper_subset(&Interval::new(1, 2)), false);
765    /// assert_eq!(Interval::new(3, 6).is_proper_subset(&Interval::new(4, 5)), false);
766    /// assert_eq!(Interval::new(5, 8).is_proper_subset(&Interval::new(5, 8)), false);
767    ///
768    /// assert_eq!(Interval::empty().is_proper_subset(&Interval::new(5, 8)), true);
769    /// assert_eq!(Interval::<usize>::empty().is_proper_subset(&Interval::empty()), false);
770    /// ```
771    fn is_proper_subset(&self, other: &Interval<Bound>) -> bool {
772        self.is_subset(other) && self != other
773    }
774}
775
776impl<Bound> Intersection for Interval<Bound>
777where
778    Bound: Width + Num,
779{
780    type Output = Interval<Bound>;
781
782    /// Calculates the intersection of two intervals.
783    /// ```
784    /// # use interval::prelude::*;
785    /// assert_eq!(Interval::intersection(&Interval::new(1, 4), &Interval::new(2, 6)), Interval::new(2, 4));
786    /// assert_eq!(Interval::new(1, 4).intersection(&Interval::new(2, 6)), Interval::new(2, 4));
787    ///
788    /// assert_eq!(Interval::new(6, 7).intersection(&Interval::new(3, 9)), Interval::new(6, 7));
789    /// assert_eq!(Interval::new(8, 9).intersection(&Interval::new(1, 2)), Interval::empty());
790    /// assert_eq!(Interval::new(5, 8).intersection(&Interval::new(8, 10)), Interval::singleton(8));
791    /// ```
792    fn intersection(&self, other: &Interval<Bound>) -> Interval<Bound> {
793        Interval::new(max(self.low(), other.low()), min(self.up(), other.up()))
794    }
795}
796
797impl<Bound> Intersection<Bound> for Interval<Bound>
798where
799    Bound: Width + Num,
800{
801    type Output = Interval<Bound>;
802    /// Calculates whether value is contained in an interval.
803    /// Returns the value if it is in the interval.
804    /// ```
805    /// # use interval::prelude::*;
806    /// assert_eq!(Interval::new(3, 8).intersection(&4), Interval::singleton(4));
807    /// assert_eq!(Interval::new(7, 9).intersection(&9), Interval::singleton(9));
808    /// assert_eq!(Interval::new(1, 4).intersection(&1), Interval::singleton(1));
809    /// assert_eq!(Interval::empty().intersection(&9), Interval::empty());
810    /// ```
811
812    fn intersection(&self, value: &Bound) -> Interval<Bound> {
813        if self.contains(value) {
814            Interval::singleton(value.clone())
815        } else {
816            Interval::empty()
817        }
818    }
819}
820
821impl<Bound> Intersection<Optional<Bound>> for Interval<Bound>
822where
823    Bound: Width + Num,
824{
825    type Output = Interval<Bound>;
826
827    /// Calculates whether an optional is contained in an interval.
828    /// Returns the optional if it is in the interval.
829    /// ```
830    /// # use interval::prelude::*;
831    /// assert_eq!(Interval::new(3, 8).intersection(&Optional::singleton(4)), Interval::singleton(4));
832    /// assert_eq!(Interval::new(7, 9).intersection(&Optional::singleton(9)), Interval::singleton(9));
833    /// assert_eq!(Interval::new(1, 4).intersection(&Optional::singleton(0)), Interval::empty());
834    /// assert_eq!(Interval::empty().intersection(&Optional::singleton(9)), Interval::empty());
835    /// assert_eq!(Interval::new(2, 6).intersection(&Optional::empty()), Interval::empty());
836    /// ```
837    fn intersection(&self, value: &Optional<Bound>) -> Interval<Bound> {
838        value
839            .as_ref()
840            .map_or(Interval::empty(), |x| self.intersection(x))
841    }
842}
843
844macro_rules! optional_interval_intersection
845{
846  ( $( $source:ty ),* ) =>
847  {$(
848    impl Intersection<Interval<$source>> for Optional<$source>
849    {
850      type Output = Optional<$source>;
851      #[doc = concat!(
852        r#"
853        Calculates whether the optional is contained in an interval.
854        ```
855        # use interval::prelude::*;
856        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(4).intersection(&Interval::new(3, 8)), Optional::singleton(4));
857        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(9).intersection(&Interval::new(7, 9)), Optional::singleton(9));
858        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(0).intersection(&Interval::new(1, 4)), Optional::empty());
859        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(9).intersection(&Interval::empty()), Optional::empty());
860        assert_eq!(Optional::<"#, stringify!($source), r#">::empty().intersection(&Interval::new(2, 6)), Optional::empty());
861        ```
862        "#
863      )]
864      fn intersection(&self, other: &Interval<$source>) -> Optional<$source> {
865        self.as_ref().map_or(Optional::empty(), |x| other.intersection(x).into_optional())
866      }
867    }
868  )*}
869}
870
871optional_interval_intersection!(i8, u8, i16, u16, i32, u32, i64, u64, isize, usize);
872
873impl<Bound> Difference for Interval<Bound>
874where
875    Bound: Width + Num,
876{
877    type Output = Interval<Bound>;
878
879    /// Calculates the interval covering values in the left interval but not the right interval.
880    /// ```
881    /// # use interval::prelude::*;
882    /// assert_eq!(Interval::new(4, 9).difference(&Interval::new(6, 11)), Interval::new(4, 5));
883    /// // The lower [1, 2] and higher [3, 10] values are included, and the smallest interval containing them is [1, 10].
884    /// assert_eq!(Interval::new(1, 10).difference(&Interval::new(2, 3)), Interval::new(1, 10));
885    /// // 5 is included in both intervals so the difference starts at 6.
886    /// assert_eq!(Interval::new(4, 7).difference(&Interval::new(4, 5)), Interval::new(6, 7));
887    /// assert_eq!(Interval::new(2, 3).difference(&Interval::new(1, 10)), Interval::empty());
888    /// assert_eq!(Interval::new(5, 6).difference(&Interval::empty()), Interval::new(5, 6));
889    /// assert_eq!(Interval::empty().difference(&Interval::new(2, 6)), Interval::empty());
890    /// ```
891    fn difference(&self, other: &Interval<Bound>) -> Interval<Bound> {
892        // A - B is equivalent to A /\ ~B
893        // However the complement operation doesn't make sense here
894        // because it'd nearly always ends up to the whole integer interval.
895        // Instead we use this equivalence:
896        //   A - B is equivalent to:
897        //      A /\ [inf,B.lb-1]
898        //    \/
899        //      A /\ [B.ub+1, inf]
900        let left = self.intersection(&Interval::min_lb(other.low() - Bound::one()));
901        let right = self.intersection(&Interval::max_ub(other.up() + Bound::one()));
902        left.hull(&right)
903    }
904}
905
906impl<Bound> Difference<Bound> for Interval<Bound>
907where
908    Bound: Num + Clone,
909{
910    type Output = Interval<Bound>;
911
912    /// Calculates the interval covering values in the left interval, excluding `value`.
913    /// ```
914    /// # use interval::prelude::*;
915    /// // 5 is included in the interval but the smallest interval covering the new range is [4, 9].
916    /// assert_eq!(Interval::new(4, 9).difference(&5), Interval::new(4, 9));
917    /// assert_eq!(Interval::new(1, 5).difference(&7), Interval::new(1, 5));
918    /// assert_eq!(Interval::new(4, 7).difference(&4), Interval::new(5, 7));
919    /// assert_eq!(Interval::new(2, 6).difference(&6), Interval::new(2, 5));
920    /// assert_eq!(Interval::new(8, 8).difference(&8), Interval::empty());
921    /// assert_eq!(Interval::empty().difference(&2), Interval::empty());
922    /// ```
923    fn difference(&self, value: &Bound) -> Interval<Bound> {
924        let mut this = self.clone();
925        if value == &this.lb {
926            this.lb = this.lb + Bound::one();
927        } else if value == &this.ub {
928            this.ub = this.ub - Bound::one();
929        }
930        this
931    }
932}
933
934impl<Bound> Difference<Optional<Bound>> for Interval<Bound>
935where
936    Bound: Ord + Num + Clone,
937{
938    type Output = Interval<Bound>;
939
940    /// Calculates the interval covering values in the left interval, excluding `value`.
941    /// See [`Difference<Bound>`](#method.difference-1) for details of when the `Optional` contains a value.
942    /// ```
943    /// # use interval::prelude::*;
944    /// assert_eq!(Interval::new(4, 9).difference(&Optional::singleton(5)), Interval::new(4, 9));
945    /// assert_eq!(Interval::new(3, 5).difference(&Optional::empty()), Interval::new(3, 5));
946    /// assert_eq!(Interval::new(8, 8).difference(&Optional::empty()), Interval::new(8, 8));
947    /// ```
948    fn difference(&self, value: &Optional<Bound>) -> Interval<Bound> {
949        value
950            .as_ref()
951            .map_or_else(|| self.clone(), |x| self.difference(x))
952    }
953}
954
955macro_rules! optional_interval_difference
956{
957  ( $( $source:ty ),* ) =>
958  {$(
959    impl Difference<Interval<$source>> for Optional<$source>
960    {
961      type Output = Optional<$source>;
962      #[doc = concat!(
963        r#"
964        Calculates whether an optional is outside of an interval.
965        ```
966        # use interval::prelude::*;
967        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(4).difference(&Interval::new(3, 8)), Optional::empty());
968        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(8).difference(&Interval::new(7, 9)), Optional::empty());
969        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(3).difference(&Interval::new(1, 4)), Optional::empty());
970        assert_eq!(Optional::<"#, stringify!($source), r#">::singleton(9).difference(&Interval::empty()), Optional::singleton(9));
971        assert_eq!(Optional::<"#, stringify!($source), r#">::empty().difference(&Interval::new(2, 6)), Optional::empty());
972        ```
973      "#)]
974      fn difference(&self, other: &Interval<$source>) -> Optional<$source> {
975        self.as_ref().map_or(Optional::empty(), |x|
976          if other.contains(x) { Optional::empty() }
977          else { Optional::singleton(x.clone()) }
978        )
979      }
980    }
981  )*}
982}
983
984optional_interval_difference!(i8, u8, i16, u16, i32, u32, i64, u64, isize, usize);
985
986impl<Bound> ShrinkLeft for Interval<Bound>
987where
988    Bound: Num + Width,
989{
990    /// Updates the lower bound to be greater than or equal to a value.
991    /// ```
992    /// use interval::prelude::*;
993    /// let a = Interval::new(5, 9);
994    /// // Increase the lower bound.
995    /// let b = a.shrink_left(7);
996    /// assert_eq!(b, Interval::new(7, 9));
997    /// // No effect on the lower bound.
998    /// let c = a.shrink_left(4);
999    /// assert_eq!(c, a);
1000    /// // Empty interval.
1001    /// let d = a.shrink_left(10);
1002    /// assert!(d.is_empty());
1003    /// ```
1004    fn shrink_left(&self, lb: Bound) -> Interval<Bound> {
1005        let mut this = self.clone();
1006        if lb > this.lb {
1007            this.lb = lb;
1008        }
1009        this
1010    }
1011}
1012
1013impl<Bound> ShrinkRight for Interval<Bound>
1014where
1015    Bound: Num + Width,
1016{
1017    /// Updates the upper bound to be less than or equal to a value.
1018    /// ```
1019    /// use interval::prelude::*;
1020    /// let a = Interval::new(5, 9);
1021    /// // Decrease the upper bound.
1022    /// let b = a.shrink_right(8);
1023    /// assert_eq!(b, Interval::new(5, 8));
1024    /// // No effect on the upper bound.
1025    /// let c = a.shrink_right(12);
1026    /// assert_eq!(c, a);
1027    /// // Empty interval.
1028    /// let d = a.shrink_right(3);
1029    /// assert!(d.is_empty());
1030    /// ```
1031    fn shrink_right(&self, ub: Bound) -> Interval<Bound> {
1032        let mut this = self.clone();
1033        if ub < this.ub {
1034            this.ub = ub;
1035        }
1036        this
1037    }
1038}
1039
1040forward_all_binop!(impl<Bound: +Num+Width> Add for Interval<Bound>, add);
1041
1042impl<'a, 'b, Bound> Add<&'b Interval<Bound>> for &'a Interval<Bound>
1043where
1044    Bound: Num + Width,
1045{
1046    type Output = Interval<Bound>;
1047
1048    /// Adds two intervals, by adding the lower and upper bounds to calculate a new interval.
1049    /// ```
1050    /// # use interval::prelude::*;
1051    /// let a = Interval::new(5, 9);
1052    /// let b = Interval::new(-2, 4);
1053    /// assert_eq!(a + b, Interval::new(3, 13));
1054    /// ```
1055    /// This method preserves empty intervals.
1056    /// ```
1057    /// # use interval::prelude::*;
1058    /// let a = Interval::new(5, 9);
1059    /// let b = Interval::empty();
1060    /// assert!((a + b).is_empty());
1061    /// ```
1062    fn add(self, other: &Interval<Bound>) -> Interval<Bound> {
1063        if self.is_empty() || other.is_empty() {
1064            Interval::empty()
1065        } else {
1066            Interval::new(self.lower() + other.lower(), self.upper() + other.upper())
1067        }
1068    }
1069}
1070
1071forward_all_binop!(impl<Bound: +Num+Width+Clone> Add for Interval<Bound>, add, Bound);
1072
1073impl<'a, 'b, Bound> Add<&'b Bound> for &'a Interval<Bound>
1074where
1075    Bound: Num + Width + Clone,
1076{
1077    type Output = Interval<Bound>;
1078
1079    /// Adds a constant to an interval.
1080    /// ```
1081    /// # use interval::prelude::*;
1082    /// assert_eq!(Interval::new(5, 9) + 4, Interval::new(9, 13));
1083    /// ```
1084    /// This method preserves empty intervals.
1085    /// ```
1086    /// # use interval::prelude::*;
1087    /// assert!((Interval::empty() + 4).is_empty());
1088    /// ```
1089    /// It is not possible to add an interval to a constant.
1090    /// ```compile_fail
1091    /// # use interval::prelude::*;
1092    /// let _ = 4 + Interval::new(5, 9); // doesn't compile
1093    /// ```
1094    fn add(self, other: &Bound) -> Interval<Bound> {
1095        if self.is_empty() {
1096            Interval::empty()
1097        } else {
1098            Interval::new(self.lower() + other.clone(), self.upper() + other.clone())
1099        }
1100    }
1101}
1102
1103forward_all_binop!(impl<Bound: +Num+Width> Sub for Interval<Bound>, sub);
1104
1105impl<'a, 'b, Bound> Sub<&'b Interval<Bound>> for &'a Interval<Bound>
1106where
1107    Bound: Num + Width,
1108{
1109    type Output = Interval<Bound>;
1110
1111    /// Subtracts two intervals to calculate the interval of the result.
1112    /// The upper bound of `a - b` is `a.upper() - b.lower()` and
1113    /// the lower bound is `a.lower() - b.upper()`.
1114    /// ```
1115    /// # use interval::prelude::*;
1116    /// let a = Interval::new(5, 9);
1117    /// let b = Interval::new(-2, 4);
1118    /// assert_eq!(a - b, Interval::new(1, 11));
1119    /// ```
1120    /// This method preserves empty intervals.
1121    /// ```
1122    /// # use interval::prelude::*;
1123    /// let a = Interval::new(5, 9);
1124    /// let b = Interval::empty();
1125    /// assert!((a - b).is_empty());
1126    /// ```
1127    fn sub(self, other: &Interval<Bound>) -> Interval<Bound> {
1128        if self.is_empty() || other.is_empty() {
1129            Interval::empty()
1130        } else {
1131            Interval::new(self.lower() - other.upper(), self.upper() - other.lower())
1132        }
1133    }
1134}
1135
1136forward_all_binop!(impl<Bound: +Num+Width+Clone> Sub for Interval<Bound>, sub, Bound);
1137
1138impl<'a, 'b, Bound> Sub<&'b Bound> for &'a Interval<Bound>
1139where
1140    Bound: Num + Width + Clone,
1141{
1142    type Output = Interval<Bound>;
1143
1144    /// Subtracts a constant from an interval.
1145    /// ```
1146    /// # use interval::prelude::*;
1147    /// assert_eq!(Interval::new(5, 9) - 4, Interval::new(1, 5));
1148    /// ```
1149    /// This method preserves empty intervals.
1150    /// ```
1151    /// # use interval::prelude::*;
1152    /// assert!((Interval::empty() - 4).is_empty());
1153    /// ```
1154    /// It is not possible to subtract an interval from a constant.
1155    /// ```compile_fail
1156    /// # use interval::prelude::*;
1157    /// let _ = 4 - Interval::new(5, 9); // doesn't compile
1158    /// ```
1159    fn sub(self, other: &Bound) -> Interval<Bound> {
1160        if self.is_empty() {
1161            Interval::empty()
1162        } else {
1163            Interval::new(self.lower() - other.clone(), self.upper() - other.clone())
1164        }
1165    }
1166}
1167
1168forward_all_binop!(impl<Bound: +Num+Width> Mul for Interval<Bound>, mul);
1169
1170// Adapted from the code found in the Rust compiler sources.
1171// Rational: min_max was removed.
1172fn min_max<Iter, Item>(mut iter: Iter) -> (Item, Item)
1173where
1174    Iter: Iterator<Item = Item>,
1175    Item: Ord,
1176{
1177    debug_assert!(
1178        iter.size_hint().0 > 2,
1179        "`min_max` expects an iterator (`iter`) yielding at least two elements."
1180    );
1181    let (mut min, mut max) = {
1182        let x = iter.next().unwrap();
1183        let y = iter.next().unwrap();
1184        if x <= y {
1185            (x, y)
1186        } else {
1187            (y, x)
1188        }
1189    };
1190
1191    loop {
1192        // `first` and `second` are the two next elements we want to look
1193        // at.  We first compare `first` and `second` (#1). The smaller one
1194        // is then compared to current minimum (#2). The larger one is
1195        // compared to current maximum (#3). This way we do 3 comparisons
1196        // for 2 elements.
1197        let first = match iter.next() {
1198            None => break,
1199            Some(x) => x,
1200        };
1201        let second = match iter.next() {
1202            None => {
1203                if first < min {
1204                    min = first;
1205                } else if first >= max {
1206                    max = first;
1207                }
1208                break;
1209            }
1210            Some(x) => x,
1211        };
1212        if first <= second {
1213            if first < min {
1214                min = first
1215            }
1216            if second >= max {
1217                max = second
1218            }
1219        } else {
1220            if second < min {
1221                min = second
1222            }
1223            if first >= max {
1224                max = first
1225            }
1226        }
1227    }
1228    (min, max)
1229}
1230
1231impl<'a, 'b, Bound> Mul<&'b Interval<Bound>> for &'a Interval<Bound>
1232where
1233    Bound: Num + Width,
1234{
1235    type Output = Interval<Bound>;
1236
1237    /// Multiplies two intervals by multiplying the lower and upper bounds.
1238    /// Caution: the resulting interval is often an over-approximation.
1239    /// ```
1240    /// # use interval::prelude::*;
1241    /// assert_eq!(Interval::new(0, 1) * Interval::new(3, 5), Interval::new(0, 5));
1242    /// ```
1243    /// The interval produced is the smallest possible interval,
1244    /// however, only the values 0, 3, 4 and 5 are possible results of this multiplication.
1245    ///
1246    /// This method preserves empty intervals.
1247    /// ```
1248    /// # use interval::prelude::*;
1249    /// assert!((Interval::empty() * Interval::new(2, 4)).is_empty());
1250    /// ```
1251    fn mul(self, other: &Interval<Bound>) -> Interval<Bound> {
1252        if self.is_empty() || other.is_empty() {
1253            Interval::empty()
1254        } else {
1255            let (min, max) = min_max(
1256                vec![
1257                    self.lower() * other.lower(),
1258                    self.lower() * other.upper(),
1259                    self.upper() * other.lower(),
1260                    self.upper() * other.upper(),
1261                ]
1262                .into_iter(),
1263            );
1264            Interval::new(min, max)
1265        }
1266    }
1267}
1268
1269forward_all_binop!(impl<Bound: +Num+Width+Clone> Mul for Interval<Bound>, mul, Bound);
1270
1271impl<'a, 'b, Bound> Mul<&'b Bound> for &'a Interval<Bound>
1272where
1273    Bound: Num + Width + Clone,
1274{
1275    type Output = Interval<Bound>;
1276
1277    /// Multiplies an interval by a constant.
1278    /// Caution: the resulting interval is often an over-approximation.
1279    /// ```
1280    /// # use interval::prelude::*;
1281    /// assert_eq!(Interval::new(0, 1) * 3, Interval::new(0, 3));
1282    /// ```
1283    /// The interval produced is the smallest possible interval,
1284    /// however, only the values 0 and 3 are possible results of this multiplication.
1285    ///
1286    /// This method preserves empty intervals.
1287    /// ```
1288    /// # use interval::prelude::*;
1289    /// assert!((Interval::empty() * 4).is_empty());
1290    /// ```
1291    /// It is not possible to multiply a constant by an interval.
1292    /// ```compile_fail
1293    /// # use interval::prelude::*;
1294    /// let _ = 4 * Interval::new(5, 9); // doesn't compile
1295    /// ```
1296    fn mul(self, other: &Bound) -> Interval<Bound> {
1297        if self.is_empty() {
1298            Interval::empty()
1299        } else {
1300            Interval::new(self.lower() * other.clone(), self.upper() * other.clone())
1301        }
1302    }
1303}
1304
1305impl<Bound> Display for Interval<Bound>
1306where
1307    Bound: Display + Width + Num,
1308{
1309    /// Formats an interval.
1310    /// Empty intervals are displayed as the empty set "{}".
1311    /// Non empty intervals are displayed as [lower..upper].
1312    /// ```
1313    /// # use interval::prelude::*;
1314    /// assert_eq!(format!("{}", Interval::new(3, 5)), "[3..5]");
1315    /// assert_eq!(format!("{}", Interval::singleton(4)), "[4..4]");
1316    /// assert_eq!(format!("{}", Interval::<usize>::empty()), "{}");
1317    /// ```
1318    fn fmt(&self, formatter: &mut Formatter) -> Result<(), Error> {
1319        if self.is_empty() {
1320            formatter.write_str("{}")
1321        } else {
1322            formatter.write_fmt(format_args!("[{}..{}]", self.lb, self.ub))
1323        }
1324    }
1325}
1326
1327pub trait ToInterval<Bound> {
1328    /// Converts a value to an interval.
1329    /// For example,
1330    /// ```
1331    /// # use interval::prelude::*;
1332    /// assert_eq!(8.to_interval(), Interval::singleton(8));
1333    /// assert_eq!((3, 4).to_interval(), Interval::new(3, 4));
1334    /// assert_eq!(().to_interval(), Interval::<usize>::empty());
1335    /// ```
1336    fn to_interval(self) -> Interval<Bound>;
1337}
1338
1339impl<Bound> ToInterval<Bound> for Interval<Bound> {
1340    /// Converts an interval to an interval with no action.
1341    /// ```
1342    /// # use interval::prelude::*;
1343    /// let interval = Interval::new(2, 6);
1344    /// assert_eq!(interval.to_interval(), interval);
1345    ///
1346    /// let empty = Interval::<i16>::empty();
1347    /// assert_eq!(empty.to_interval(), empty);
1348    /// ```
1349    fn to_interval(self) -> Interval<Bound> {
1350        self
1351    }
1352}
1353
1354impl<Bound: Width + Num> ToInterval<Bound> for (Bound, Bound) {
1355    /// Converts a tuple to an interval using the first element as the lower bound
1356    /// and second element as the upper bound.
1357    /// ```
1358    /// # use interval::prelude::*;
1359    /// assert_eq!((2, 6).to_interval(), Interval::new(2, 6));
1360    /// ```
1361    /// The first and second elements need the same type.
1362    /// ```compile_fail
1363    /// # use interval::prelude::*;
1364    /// let _ = (8 as u8, 9 as i8).to_interval(); // doesn't compile
1365    /// ```
1366    fn to_interval(self) -> Interval<Bound> {
1367        let (a, b) = self;
1368        Interval::new(a, b)
1369    }
1370}
1371
1372impl<Bound: Width + Num> ToInterval<Bound> for () {
1373    /// Converts the empty tuple to an empty interval.
1374    /// ```
1375    /// # use interval::prelude::*;
1376    /// assert_eq!(().to_interval(), Interval::<usize>::empty());
1377    /// ```
1378    /// The type can be specified via the full trait or annotations.
1379    /// ```
1380    /// # use interval::prelude::*;
1381    /// let empty_full_trait = ToInterval::<i32>::to_interval(());
1382    /// let empty_annotated: Interval<i32> = ().to_interval();
1383    /// assert_eq!(empty_full_trait, Interval::empty());
1384    /// assert_eq!(empty_annotated, Interval::empty());
1385    /// ```
1386    fn to_interval(self) -> Interval<Bound> {
1387        Interval::empty()
1388    }
1389}
1390
1391impl<Bound: Width + Num> ToInterval<Bound> for Bound {
1392    /// Converts a value to a singleton interval.
1393    /// ```
1394    /// # use interval::prelude::*;
1395    /// assert_eq!(9.to_interval(), Interval::singleton(9));
1396    /// ```
1397    fn to_interval(self) -> Interval<Bound> {
1398        Interval::singleton(self)
1399    }
1400}
1401
1402impl<Bound: Width + Num> ToInterval<Bound> for RangeInclusive<Bound> {
1403    /// Converts an inclusive range to an interval.
1404    /// ```
1405    /// # use interval::prelude::*;
1406    /// let range = 2..=6; // out of bounds for Width trait
1407    /// assert_eq!(range.to_interval(), Interval::new(2, 6));
1408    /// ```
1409    /// The inclusive range is required because the endpoints are included in the interval.
1410    /// Therefore, the semi-exclusive range fails to compile.
1411    /// ```compile_fail
1412    /// # use interval::prelude::*;
1413    /// let range = 2..6; // semi-exclusive range
1414    /// let _ = range.to_interval(); // fail
1415    /// ```
1416    fn to_interval(self) -> Interval<Bound> {
1417        Interval::new(self.start().clone(), self.end().clone())
1418    }
1419}
1420
1421impl<Bound: Width + Num> ToInterval<Bound> for RangeFrom<Bound> {
1422    /// Converts a range with a lower bound to an interval.
1423    /// ```
1424    /// # use interval::prelude::*;
1425    /// let range = 2..;
1426    /// assert_eq!(range.to_interval(), Interval::new(2, <i32 as Width>::max_value()));
1427    /// ```
1428    /// See [`Interval::whole`] for caveats on the lower bound,
1429    /// which means the following example fails to compile:
1430    /// ```should_panic
1431    /// # use interval::prelude::*;
1432    /// let range = 255u8..; // out of bounds for Width trait
1433    /// let _ = range.to_interval(); // fail
1434    /// ```
1435    fn to_interval(self) -> Interval<Bound> {
1436        Interval::new(
1437            self.start.clone(),
1438            max(<Bound as Width>::max_value(), self.start.clone()),
1439        )
1440    }
1441}
1442
1443impl<Bound: Width + Num> ToInterval<Bound> for RangeToInclusive<Bound> {
1444    /// Converts a range with an upper bound to an interval.
1445    /// ```
1446    /// # use interval::prelude::*;
1447    /// let range = 0..=100u32;
1448    /// assert_eq!(range.to_interval(), Interval::new(0, 100));
1449    /// ```
1450    /// As with [`RangeInclusive`](#impl-ToInterval<Bound>-for-RangeInclusive<Bound>), the endpoint must be included:
1451    /// ```compile_fail
1452    /// # use interval::prelude::*;
1453    /// let range = ..100; // exclusive range
1454    /// let _ = range.to_interval(); // fail
1455    /// ```
1456    /// See [`Interval::whole`] for caveats on the upper bound,
1457    /// which means the following example fails to compile:
1458    /// ```should_panic
1459    /// # use interval::prelude::*;
1460    /// let range =..=255u8;
1461    /// let _ = range.to_interval(); // fail
1462    /// ```
1463    fn to_interval(self) -> Interval<Bound> {
1464        Interval::new(
1465            min(<Bound as Width>::min_value(), self.end.clone()),
1466            self.end.clone(),
1467        )
1468    }
1469}
1470
1471impl<Bound> Join for Interval<Bound>
1472where
1473    Bound: Width + Num,
1474{
1475    fn join(self, other: Interval<Bound>) -> Interval<Bound> {
1476        self.intersection(&other)
1477    }
1478}
1479
1480impl<Bound> Meet for Interval<Bound>
1481where
1482    Bound: Width + Num,
1483{
1484    fn meet(self, other: Interval<Bound>) -> Interval<Bound> {
1485        self.hull(&other)
1486    }
1487}
1488
1489impl<Bound> Entailment for Interval<Bound>
1490where
1491    Bound: Width + Num,
1492{
1493    fn entail(&self, other: &Interval<Bound>) -> SKleene {
1494        if self.is_subset(other) {
1495            SKleene::True
1496        } else if other.is_subset(self) {
1497            SKleene::False
1498        } else {
1499            SKleene::Unknown
1500        }
1501    }
1502}
1503
1504impl<Bound> Top for Interval<Bound>
1505where
1506    Bound: Width + Num,
1507{
1508    fn top() -> Interval<Bound> {
1509        Interval::empty()
1510    }
1511}
1512
1513impl<Bound> Bot for Interval<Bound>
1514where
1515    Bound: Width + Num,
1516{
1517    fn bot() -> Interval<Bound> {
1518        Interval::whole()
1519    }
1520}
1521
1522#[allow(non_upper_case_globals)]
1523#[cfg(test)]
1524mod tests {
1525    use serde_test::{assert_de_tokens, assert_de_tokens_error, assert_tokens, Token};
1526
1527    use super::*;
1528
1529    const empty: Interval<i32> = Interval { lb: 1, ub: 0 };
1530    const invalid: Interval<i32> = Interval { lb: 10, ub: -10 };
1531    const zero: Interval<i32> = Interval { lb: 0, ub: 0 };
1532    const one: Interval<i32> = Interval { lb: 1, ub: 1 };
1533    const ten: Interval<i32> = Interval { lb: 10, ub: 10 };
1534
1535    const i0_1: Interval<i32> = Interval { lb: 0, ub: 1 };
1536    const i0_2: Interval<i32> = Interval { lb: 0, ub: 2 };
1537    const i1_2: Interval<i32> = Interval { lb: 1, ub: 2 };
1538    const i0_10: Interval<i32> = Interval { lb: 0, ub: 10 };
1539    const i1_10: Interval<i32> = Interval { lb: 1, ub: 10 };
1540    const i0_9: Interval<i32> = Interval { lb: 0, ub: 9 };
1541    const i0_15: Interval<i32> = Interval { lb: 0, ub: 15 };
1542    const im5_10: Interval<i32> = Interval { lb: -5, ub: 10 };
1543    const im5_m1: Interval<i32> = Interval { lb: -5, ub: -1 };
1544    const i5_10: Interval<i32> = Interval { lb: 5, ub: 10 };
1545    const i6_10: Interval<i32> = Interval { lb: 6, ub: 10 };
1546    const i0_5: Interval<i32> = Interval { lb: 0, ub: 5 };
1547    const i0_4: Interval<i32> = Interval { lb: 0, ub: 4 };
1548    const im5_5: Interval<i32> = Interval { lb: -5, ub: 5 };
1549    const i20_30: Interval<i32> = Interval { lb: 20, ub: 30 };
1550    const im30_m20: Interval<i32> = Interval { lb: -30, ub: -20 };
1551
1552    #[test]
1553    fn to_interval_id_test() {
1554        let id = i1_2.clone().to_interval();
1555        assert_eq!(i1_2, id);
1556        assert_eq!(i1_2, Interval::new(1, 2));
1557    }
1558
1559    #[test]
1560    fn equality_test() {
1561        assert_eq!(empty, empty);
1562        assert_eq!(empty, invalid);
1563        assert_eq!(invalid, empty);
1564        assert_eq!(i1_2, i1_2);
1565    }
1566
1567    #[test]
1568    fn size_test() {
1569        let whole_i32: Interval<i32> = Interval::<i32>::whole();
1570        let whole_u32: Interval<u32> = Interval::<u32>::whole();
1571
1572        assert_eq!(zero.size(), 1);
1573        assert_eq!(one.size(), 1);
1574        assert_eq!(empty.size(), 0);
1575        assert_eq!(invalid.size(), 0);
1576
1577        assert_eq!(i1_2.size(), 2);
1578        assert_eq!(i0_10.size(), 11);
1579        assert_eq!(im30_m20.size(), 11);
1580
1581        assert_eq!(whole_i32.size(), u32::max_value());
1582        assert_eq!(whole_u32.size(), u32::max_value());
1583    }
1584
1585    #[test]
1586    fn contains_test() {
1587        assert!(i1_2.contains(&1));
1588        assert!(i1_2.contains(&2));
1589        assert!(!i1_2.contains(&0));
1590        assert!(!i1_2.contains(&3));
1591
1592        assert!(zero.contains(&0));
1593        assert!(!zero.contains(&1));
1594
1595        assert!(!empty.contains(&0));
1596        assert!(!empty.contains(&1));
1597        assert!(!empty.contains(&5));
1598        assert!(!empty.contains(&-5));
1599
1600        assert!(!invalid.contains(&0));
1601        assert!(!invalid.contains(&-11));
1602        assert!(!invalid.contains(&11));
1603    }
1604
1605    #[test]
1606    fn is_subset_test() {
1607        let cases = vec![
1608            (zero, zero, true),
1609            (i1_2, i1_2, true),
1610            (empty, empty, true),
1611            (invalid, invalid, true),
1612        ];
1613
1614        // For each cases (x, y, res)
1615        // * x and y are the values
1616        // * res is a tuple (r, sym) where
1617        //    * r is true if x is a subset of y
1618        //    * sym is true if y is a subset of x
1619        let sym_cases = vec![
1620            // ||
1621            // |-|
1622            (empty, zero, (true, false)),
1623            (invalid, zero, (true, false)),
1624            (empty, invalid, (true, true)),
1625            // ||
1626            //|--|
1627            (empty, i1_2, (true, false)),
1628            (empty, i0_10, (true, false)),
1629            (invalid, i1_2, (true, false)),
1630            //  |--|
1631            // |----|
1632            (i1_2, i0_10, (true, false)),
1633            // |--|
1634            //     |--|
1635            (i0_4, i5_10, (false, false)),
1636            // |--|
1637            //    |--|
1638            (i0_5, i5_10, (false, false)),
1639            // |---|
1640            //   |---|
1641            (im5_5, i0_10, (false, false)),
1642            // |--|
1643            //         |--|
1644            (i0_10, i20_30, (false, false)),
1645            // |--|
1646            // |---|
1647            (i0_10, i0_15, (true, false)),
1648            // |---|
1649            //  |--|
1650            (im5_10, i0_10, (false, true)),
1651        ];
1652
1653        for (x, y, r) in cases.into_iter() {
1654            assert!(
1655                x.is_subset(&y) == r,
1656                "{:?} is subset of {:?} is not equal to {:?}",
1657                x,
1658                y,
1659                r
1660            );
1661        }
1662
1663        for (x, y, (r1, r2)) in sym_cases.into_iter() {
1664            assert!(
1665                x.is_subset(&y) == r1,
1666                "{:?} is subset of {:?} is not equal to {:?}",
1667                x,
1668                y,
1669                r1
1670            );
1671            assert!(
1672                y.is_subset(&x) == r2,
1673                "{:?} is subset of {:?} is not equal to {:?}",
1674                y,
1675                x,
1676                r2
1677            );
1678        }
1679    }
1680
1681    #[test]
1682    fn is_proper_subset_test() {
1683        let cases = vec![
1684            (zero, zero, false),
1685            (i1_2, i1_2, false),
1686            (empty, empty, false),
1687            (invalid, invalid, false),
1688        ];
1689
1690        // For each cases (x, y, res)
1691        // * x and y are the values
1692        // * res is a tuple (r, sym) where
1693        //    * r is true if x is a proper subset of y
1694        //    * sym is true if y is a proper subset of x
1695        let sym_cases = vec![
1696            // ||
1697            // |-|
1698            (empty, zero, (true, false)),
1699            (invalid, zero, (true, false)),
1700            (empty, invalid, (false, false)),
1701            // ||
1702            //|--|
1703            (empty, i1_2, (true, false)),
1704            (empty, i0_10, (true, false)),
1705            (invalid, i1_2, (true, false)),
1706            //  |--|
1707            // |----|
1708            (i1_2, i0_10, (true, false)),
1709            // |--|
1710            //     |--|
1711            (i0_4, i5_10, (false, false)),
1712            // |--|
1713            //    |--|
1714            (i0_5, i5_10, (false, false)),
1715            // |---|
1716            //   |---|
1717            (im5_5, i0_10, (false, false)),
1718            // |--|
1719            //         |--|
1720            (i0_10, i20_30, (false, false)),
1721            // |--|
1722            // |---|
1723            (i0_10, i0_15, (true, false)),
1724            // |---|
1725            //  |--|
1726            (im5_10, i0_10, (false, true)),
1727        ];
1728
1729        for (x, y, r) in cases.into_iter() {
1730            assert!(
1731                x.is_proper_subset(&y) == r,
1732                "{:?} is proper subset of {:?} is not equal to {:?}",
1733                x,
1734                y,
1735                r
1736            );
1737        }
1738
1739        for (x, y, (r1, r2)) in sym_cases.into_iter() {
1740            assert!(
1741                x.is_proper_subset(&y) == r1,
1742                "{:?} is proper subset of {:?} is not equal to {:?}",
1743                x,
1744                y,
1745                r1
1746            );
1747            assert!(
1748                y.is_proper_subset(&x) == r2,
1749                "{:?} is proper subset of {:?} is not equal to {:?}",
1750                y,
1751                x,
1752                r2
1753            );
1754        }
1755    }
1756
1757    #[test]
1758    fn intersection_test() {
1759        let cases = vec![
1760            (zero, zero, zero),
1761            (i1_2, i1_2, i1_2),
1762            (empty, empty, empty),
1763            (invalid, invalid, invalid),
1764        ];
1765
1766        // For each cases (x, y, res)
1767        // * x and y are the values
1768        // * res is the expected result, which should be the same
1769        // for x intersect y and y intersect x since the intersection
1770        // is commutative.
1771        let sym_cases = vec![
1772            // ||
1773            // |-|
1774            (empty, zero, empty),
1775            (invalid, zero, empty),
1776            (empty, invalid, empty),
1777            // ||
1778            //|--|
1779            (empty, i1_2, empty),
1780            (empty, i0_10, empty),
1781            (invalid, i1_2, empty),
1782            //  |--|
1783            // |----|
1784            (i1_2, i0_10, i1_2),
1785            // |--|
1786            //     |--|
1787            (i0_4, i5_10, empty),
1788            // |--|
1789            //    |--|
1790            (i0_5, i5_10, 5.to_interval()),
1791            // |---|
1792            //   |---|
1793            (im5_5, i0_10, (0, 5).to_interval()),
1794            // |--|
1795            //         |--|
1796            (i0_10, i20_30, empty),
1797            // |--|
1798            // |---|
1799            (i0_10, i0_15, i0_10),
1800            // |---|
1801            //  |--|
1802            (im5_10, i0_10, i0_10),
1803        ];
1804
1805        for (x, y, r) in cases.into_iter() {
1806            assert!(
1807                x.intersection(&y) == r,
1808                "{:?} intersection {:?} is not equal to {:?}",
1809                x,
1810                y,
1811                r
1812            );
1813        }
1814
1815        for (x, y, r) in sym_cases.into_iter() {
1816            assert!(
1817                x.intersection(&y) == r,
1818                "{:?} intersection {:?} is not equal to {:?}",
1819                x,
1820                y,
1821                r
1822            );
1823            assert!(
1824                y.intersection(&x) == r,
1825                "{:?} intersection {:?} is not equal to {:?}",
1826                y,
1827                x,
1828                r
1829            );
1830        }
1831    }
1832
1833    #[test]
1834    fn intersection_value_optional_test() {
1835        let cases = vec![
1836            (1, empty, None, empty, None),
1837            (2, invalid, None, empty, None),
1838            (3, empty, Some(1), empty, None),
1839            (4, i0_10, None, empty, None),
1840            (5, i0_10, Some(0), zero, Some(0)),
1841            (6, i0_10, Some(10), ten, Some(10)),
1842            (7, i0_10, Some(1), one, Some(1)),
1843            (8, i0_10, Some(-1), empty, None),
1844            (9, i0_10, Some(11), empty, None),
1845            (10, one, Some(0), empty, None),
1846            (11, one, Some(1), one, Some(1)),
1847        ];
1848        for (id, x, y, r1, r2) in cases.into_iter() {
1849            let y = y.map_or(Optional::empty(), |y| Optional::singleton(y));
1850            let r2 = r2.map_or(Optional::empty(), |r2| Optional::singleton(r2));
1851            // Interval /\ Value.
1852            if !y.is_empty() {
1853                assert!(
1854                    x.intersection(y.as_ref().unwrap()) == r1,
1855                    "Test#{}: {:?} intersection {:?} is not equal to {:?}",
1856                    id,
1857                    x,
1858                    y.as_ref().unwrap(),
1859                    r1
1860                );
1861            }
1862            // Interval /\ Option<T>
1863            assert!(
1864                x.intersection(&y) == r1,
1865                "Test#{}: {:?} intersection {:?} is not equal to {:?}",
1866                id,
1867                x,
1868                y,
1869                r1
1870            );
1871            // Option<T> /\ Interval
1872            assert!(
1873                y.intersection(&x) == r2,
1874                "Test#{}: {:?} intersection {:?} is not equal to {:?}",
1875                id,
1876                y,
1877                x,
1878                r2
1879            );
1880        }
1881    }
1882
1883    #[test]
1884    fn hull_test() {
1885        let cases = vec![
1886            (zero, zero, zero),
1887            (i1_2, i1_2, i1_2),
1888            (empty, empty, empty),
1889            (invalid, invalid, invalid),
1890        ];
1891
1892        // For each cases (x, y, res)
1893        // * x and y are the values
1894        // * res is the expected result, which should be the same
1895        // for the union hull of (x,y) or (y,x) since the union hull
1896        // is commutative.
1897        let sym_cases = vec![
1898            // ||
1899            // |-|
1900            (empty, zero, zero),
1901            (invalid, zero, zero),
1902            (empty, invalid, empty),
1903            // ||
1904            //|--|
1905            (empty, i1_2, i1_2),
1906            (empty, i0_10, i0_10),
1907            (invalid, i1_2, i1_2),
1908            //  |--|
1909            // |----|
1910            (i1_2, i0_10, i0_10),
1911            // |--|
1912            //     |--|
1913            (i0_4, i5_10, i0_10),
1914            // |--|
1915            //    |--|
1916            (i0_5, i5_10, i0_10),
1917            // |---|
1918            //   |---|
1919            (im5_5, i0_10, (-5, 10).to_interval()),
1920            // |--|
1921            //         |--|
1922            (i0_10, i20_30, (0, 30).to_interval()),
1923            // |--|
1924            // |---|
1925            (i0_10, i0_15, i0_15),
1926            // |---|
1927            //  |--|
1928            (im5_10, i0_10, im5_10),
1929        ];
1930
1931        for (x, y, r) in cases.into_iter() {
1932            assert!(
1933                x.hull(&y) == r,
1934                "{:?} hull {:?} is not equal to {:?}",
1935                x,
1936                y,
1937                r
1938            );
1939        }
1940
1941        for (x, y, r) in sym_cases.into_iter() {
1942            assert!(
1943                x.hull(&y) == r,
1944                "{:?} hull {:?} is not equal to {:?}",
1945                x,
1946                y,
1947                r
1948            );
1949            assert!(
1950                y.hull(&x) == r,
1951                "{:?} hull {:?} is not equal to {:?}",
1952                y,
1953                x,
1954                r
1955            );
1956        }
1957    }
1958
1959    #[test]
1960    fn is_disjoint_test() {
1961        let cases = vec![
1962            (zero, zero, false),
1963            (i1_2, i1_2, false),
1964            (empty, empty, true),
1965            (invalid, invalid, true),
1966        ];
1967
1968        // For each cases (x, y, res)
1969        // * x and y are the values
1970        // * res is the expected result, which should be the same
1971        // for x is disjoint of y and y is disjoint of x since the
1972        // disjoint operation is commutative.
1973        let sym_cases = vec![
1974            // ||
1975            // |-|
1976            (empty, zero, true),
1977            (invalid, zero, true),
1978            (empty, invalid, true),
1979            // ||
1980            //|--|
1981            (empty, i1_2, true),
1982            (empty, i0_10, true),
1983            (invalid, i1_2, true),
1984            //  |--|
1985            // |----|
1986            (i1_2, i0_10, false),
1987            // |--|
1988            //     |--|
1989            (i0_4, i5_10, true),
1990            // |--|
1991            //    |--|
1992            (i0_5, i5_10, false),
1993            // |---|
1994            //   |---|
1995            (im5_5, i0_10, false),
1996            // |--|
1997            //         |--|
1998            (i0_10, i20_30, true),
1999            // |--|
2000            // |---|
2001            (i0_10, i0_15, false),
2002            // |---|
2003            //  |--|
2004            (im5_10, i0_10, false),
2005        ];
2006
2007        for (x, y, r) in cases.into_iter() {
2008            assert!(
2009                x.is_disjoint(&y) == r,
2010                "{:?} is disjoint of {:?} is not equal to {:?}",
2011                x,
2012                y,
2013                r
2014            );
2015            assert!(
2016                x.overlap(&y) == !r,
2017                "{:?} overlap {:?} is not equal to {:?}",
2018                x,
2019                y,
2020                r
2021            );
2022        }
2023
2024        for (x, y, r) in sym_cases.into_iter() {
2025            assert!(
2026                x.is_disjoint(&y) == r,
2027                "{:?} is disjoint of {:?} is not equal to {:?}",
2028                x,
2029                y,
2030                r
2031            );
2032            assert!(
2033                y.is_disjoint(&x) == r,
2034                "{:?} is disjoint of {:?} is not equal to {:?}",
2035                y,
2036                x,
2037                r
2038            );
2039            assert!(
2040                x.overlap(&y) == !r,
2041                "{:?} overlap {:?} is not equal to {:?}",
2042                x,
2043                y,
2044                r
2045            );
2046            assert!(
2047                y.overlap(&x) == !r,
2048                "{:?} overlap {:?} is not equal to {:?}",
2049                y,
2050                x,
2051                r
2052            );
2053        }
2054    }
2055
2056    fn is_disjoint_cases() -> Vec<(u32, Interval<i32>, i32, bool)> {
2057        vec![
2058            (1, empty, 0, true),
2059            (2, invalid, 0, true),
2060            (3, i0_4, -1, true),
2061            (4, i0_4, 0, false),
2062            (5, i0_4, 2, false),
2063            (6, i0_4, 3, false),
2064            (7, i0_4, 5, true),
2065        ]
2066    }
2067
2068    #[test]
2069    fn is_disjoint_bound_test() {
2070        let cases = is_disjoint_cases();
2071        for (id, x, y, r) in cases.into_iter() {
2072            assert!(
2073                x.is_disjoint(&y) == r,
2074                "Test#{}: {:?} is disjoint of {:?} is not equal to {:?}",
2075                id,
2076                x,
2077                y,
2078                r
2079            );
2080            assert!(
2081                y.is_disjoint(&x) == r,
2082                "Test#{}: {:?} is disjoint of {:?} is not equal to {:?}",
2083                id,
2084                y,
2085                x,
2086                r
2087            );
2088            assert!(
2089                x.overlap(&y) == !r,
2090                "Test#{}: {:?} overlap {:?} is not equal to {:?}",
2091                id,
2092                x,
2093                y,
2094                !r
2095            );
2096            assert!(
2097                y.overlap(&x) == !r,
2098                "Test#{}: {:?} overlap {:?} is not equal to {:?}",
2099                id,
2100                y,
2101                x,
2102                !r
2103            );
2104        }
2105    }
2106
2107    #[test]
2108    fn is_disjoint_option_test() {
2109        let mut cases: Vec<(u32, Interval<i32>, Optional<i32>, bool)> = is_disjoint_cases()
2110            .into_iter()
2111            .map(|(id, a, b, e)| (id, a, Optional::singleton(b), e))
2112            .collect();
2113        cases.extend(vec![
2114            (8, empty, Optional::empty(), true),
2115            (9, invalid, Optional::empty(), true),
2116            (10, i0_4, Optional::empty(), true),
2117        ]);
2118        for (id, x, y, r) in cases.into_iter() {
2119            assert!(
2120                x.is_disjoint(&y) == r,
2121                "Test#{}: {:?} is disjoint of {:?} is not equal to {:?}",
2122                id,
2123                x,
2124                y,
2125                r
2126            );
2127            assert!(
2128                y.is_disjoint(&x) == r,
2129                "Test#{}: {:?} is disjoint of {:?} is not equal to {:?}",
2130                id,
2131                y,
2132                x,
2133                r
2134            );
2135            assert!(
2136                x.overlap(&y) == !r,
2137                "Test#{}: {:?} overlap {:?} is not equal to {:?}",
2138                id,
2139                x,
2140                y,
2141                !r
2142            );
2143            assert!(
2144                y.overlap(&x) == !r,
2145                "Test#{}: {:?} overlap {:?} is not equal to {:?}",
2146                id,
2147                y,
2148                x,
2149                !r
2150            );
2151        }
2152    }
2153
2154    #[test]
2155    fn difference_test() {
2156        let cases = vec![
2157            (1, zero, zero, empty),
2158            (2, i1_2, i1_2, empty),
2159            (3, empty, empty, empty),
2160            (4, invalid, invalid, empty),
2161        ];
2162
2163        // For each cases (x, y, res)
2164        // * x and y are the values
2165        // * res is a tuple (r, sym) where
2166        //    * x diff y == r
2167        //    * y diff x == sym
2168        let sym_cases = vec![
2169            // ||
2170            // |-|
2171            (5, empty, zero, (empty, zero)),
2172            (6, invalid, zero, (empty, zero)),
2173            (7, empty, invalid, (empty, empty)),
2174            // ||
2175            //|--|
2176            (8, empty, i1_2, (empty, i1_2)),
2177            (9, empty, i0_10, (empty, i0_10)),
2178            (10, invalid, i1_2, (empty, i1_2)),
2179            //  |--|
2180            // |----|
2181            (11, i1_2, i0_10, (empty, i0_10)),
2182            // |--|
2183            //     |--|
2184            (12, i0_4, i5_10, (i0_4, i5_10)),
2185            // |--|
2186            //    |--|
2187            (13, i0_5, i5_10, ((0, 4).to_interval(), i6_10)),
2188            // |---|
2189            //   |---|
2190            (14, im5_5, i0_10, (im5_m1, i6_10)),
2191            // |--|
2192            //         |--|
2193            (15, i0_10, i20_30, (i0_10, i20_30)),
2194            // |--|
2195            // |---|
2196            (16, i0_10, i0_15, (empty, (11, 15).to_interval())),
2197            // |---|
2198            //  |--|
2199            (17, im5_10, i0_10, (im5_m1, empty)),
2200        ];
2201
2202        for (id, x, y, r) in cases.into_iter() {
2203            println!("Test #{}", id);
2204            assert!(
2205                x.difference(&y) == r,
2206                "{:?} difference {:?} is not equal to {:?}",
2207                x,
2208                y,
2209                r
2210            );
2211        }
2212
2213        for (id, x, y, (r1, r2)) in sym_cases.into_iter() {
2214            println!("Test #{}", id);
2215            assert!(
2216                x.difference(&y) == r1,
2217                "{:?} difference {:?} is not equal to {:?}",
2218                x,
2219                y,
2220                r1
2221            );
2222            assert!(
2223                y.difference(&x) == r2,
2224                "{:?} difference {:?} is not equal to {:?}",
2225                y,
2226                x,
2227                r2
2228            );
2229        }
2230    }
2231
2232    #[test]
2233    fn difference_value_option_test() {
2234        let cases = vec![
2235            (1, empty, None, empty, None),
2236            (2, invalid, None, empty, None),
2237            (3, empty, Some(1), empty, Some(1)),
2238            (4, i0_10, None, i0_10, None),
2239            (5, i0_10, Some(0), i1_10, None),
2240            (6, i0_10, Some(10), i0_9, None),
2241            (7, i0_10, Some(1), i0_10, None),
2242            (8, i0_10, Some(9), i0_10, None),
2243            (9, i0_10, Some(-1), i0_10, Some(-1)),
2244            (10, i0_10, Some(11), i0_10, Some(11)),
2245            (11, i0_10, Some(100), i0_10, Some(100)),
2246            (12, one, Some(1), empty, None),
2247        ];
2248        for (id, x, y, r1, r2) in cases.into_iter() {
2249            let y = y.map_or(Optional::empty(), |y| Optional::singleton(y));
2250            let r2 = r2.map_or(Optional::empty(), |r2| Optional::singleton(r2));
2251            // Interval - Value.
2252            if y.is_some() {
2253                assert!(
2254                    x.difference(y.as_ref().unwrap()) == r1,
2255                    "Test#{}: {:?} difference {:?} is not equal to {:?}",
2256                    id,
2257                    x,
2258                    y.as_ref().unwrap(),
2259                    r1
2260                );
2261            }
2262            // Interval - Option<T>
2263            assert!(
2264                x.difference(&y) == r1,
2265                "Test#{}: {:?} difference {:?} is not equal to {:?}",
2266                id,
2267                x,
2268                y,
2269                r1
2270            );
2271            // Option<T> - Interval
2272            assert!(
2273                y.difference(&x) == r2,
2274                "Test#{}: {:?} difference {:?} is not equal to {:?}",
2275                id,
2276                y,
2277                x,
2278                r2
2279            );
2280        }
2281    }
2282
2283    #[test]
2284    fn shrink_left_test() {
2285        let cases = vec![
2286            (i0_10, -5, i0_10),
2287            (i0_10, 0, i0_10),
2288            (i0_10, 1, i1_10),
2289            (i0_10, 5, i5_10),
2290            (i0_10, 10, ten),
2291            (i0_10, 11, empty),
2292            (i0_10, 100, empty),
2293            (empty, 0, empty),
2294        ];
2295        for (x, y, r) in cases.into_iter() {
2296            assert!(
2297                x.shrink_left(y) == r,
2298                "{:?} shrink_left {:?} is not equal to {:?}",
2299                x,
2300                y,
2301                r
2302            );
2303        }
2304    }
2305
2306    #[test]
2307    fn shrink_right_test() {
2308        let cases = vec![
2309            (i0_10, 15, i0_10),
2310            (i0_10, 10, i0_10),
2311            (i0_10, 9, i0_9),
2312            (i0_10, 5, i0_5),
2313            (i0_10, 0, zero),
2314            (i0_10, -1, empty),
2315            (i0_10, -100, empty),
2316            (empty, 0, empty),
2317        ];
2318        for (x, y, r) in cases.into_iter() {
2319            assert!(
2320                x.shrink_right(y) == r,
2321                "{:?} shrink_right {:?} is not equal to {:?}",
2322                x,
2323                y,
2324                r
2325            );
2326        }
2327    }
2328
2329    #[test]
2330    fn add_sub_mul_bound_test() {
2331        // For each cases (x, y, r1, r2, r3)
2332        // * x and y are the values
2333        // * r1,r2 and r3 are the results of `x + y`, `x - y` and `x * y`
2334        let cases = vec![
2335            (zero, 0, zero, zero, zero),
2336            (i1_2, 0, i1_2, i1_2, zero),
2337            (empty, 0, empty, empty, empty),
2338            (invalid, 0, empty, empty, empty),
2339            (zero, 1, one, (-1, -1).to_interval(), zero),
2340            (i1_2, 1, (2, 3).to_interval(), (0, 1).to_interval(), i1_2),
2341            (empty, 1, empty, empty, empty),
2342            (invalid, 1, empty, empty, empty),
2343            (zero, 3, (3, 3).to_interval(), (-3, -3).to_interval(), zero),
2344            (
2345                i1_2,
2346                3,
2347                (4, 5).to_interval(),
2348                (-2, -1).to_interval(),
2349                (3, 6).to_interval(),
2350            ),
2351            (empty, 3, empty, empty, empty),
2352            (invalid, 3, empty, empty, empty),
2353        ];
2354
2355        for &(x, y, r1, r2, r3) in &cases {
2356            assert!(x + y == r1, "{:?} + {:?} is not equal to {:?}", x, y, r1);
2357            assert!(x - y == r2, "{:?} - {:?} is not equal to {:?}", x, y, r2);
2358            assert!(x * y == r3, "{:?} * {:?} is not equal to {:?}", x, y, r3);
2359        }
2360    }
2361
2362    #[test]
2363    fn add_test() {
2364        // For each cases (x, y, res)
2365        // * x and y are the values
2366        // * res is the result of `x + y`
2367        let sym_cases = vec![
2368            (zero, zero, zero),
2369            (i1_2, i1_2, (2, 4).to_interval()),
2370            (empty, empty, empty),
2371            (invalid, invalid, empty),
2372            // ||
2373            // |-|
2374            (empty, zero, empty),
2375            (invalid, zero, empty),
2376            (empty, invalid, empty),
2377            // ||
2378            //|--|
2379            (empty, i1_2, empty),
2380            (empty, i0_10, empty),
2381            (invalid, i1_2, empty),
2382            (zero, i0_10, i0_10),
2383            (i1_2, i0_10, (1, 12).to_interval()),
2384            (im5_10, i0_10, (-5, 20).to_interval()),
2385            (im5_10, im30_m20, (-35, -10).to_interval()),
2386        ];
2387
2388        for &(x, y, r) in &sym_cases {
2389            assert!(x + y == r, "{:?} + {:?} is not equal to {:?}", x, y, r);
2390            assert!(y + x == r, "{:?} + {:?} is not equal to {:?}", y, x, r);
2391        }
2392    }
2393
2394    #[test]
2395    fn sub_test() {
2396        // For each cases (x, y, res)
2397        // * x and y are the values
2398        // * res is the result of `x - y`
2399        let cases = vec![
2400            (zero, zero, zero),
2401            (i1_2, i1_2, (-1, 1).to_interval()),
2402            (empty, empty, empty),
2403            (invalid, invalid, empty),
2404            // ||
2405            // |-|
2406            (empty, zero, empty),
2407            (invalid, zero, empty),
2408            (empty, invalid, empty),
2409            // ||
2410            //|--|
2411            (empty, i1_2, empty),
2412            (empty, i0_10, empty),
2413            (invalid, i1_2, empty),
2414        ];
2415
2416        // For each cases (x, y, (res1, res2))
2417        // * x and y are the values
2418        // * res1 is the result of `x - y` and res2 of `y - x`
2419        let sym_cases = vec![
2420            (zero, i0_10, ((-10, 0), (0, 10))),
2421            (i1_2, i0_10, ((-9, 2), (-2, 9))),
2422            (im5_10, i0_10, ((-15, 10), (-10, 15))),
2423            (im5_10, im30_m20, ((15, 40), (-40, -15))),
2424        ];
2425
2426        for &(x, y, r) in &cases {
2427            assert!(x - y == r, "{:?} - {:?} is not equal to {:?}", x, y, r);
2428            assert!(y - x == r, "{:?} - {:?} is not equal to {:?}", y, x, r);
2429        }
2430
2431        for &(x, y, (r1, r2)) in &sym_cases {
2432            let r1 = r1.to_interval();
2433            let r2 = r2.to_interval();
2434            assert!(x - y == r1, "{:?} - {:?} is not equal to {:?}", x, y, r1);
2435            assert!(y - x == r2, "{:?} - {:?} is not equal to {:?}", y, x, r2);
2436        }
2437    }
2438
2439    #[test]
2440    fn mul_test() {
2441        // For each cases (x, y, res)
2442        // * x and y are the values
2443        // * res is the result of `x * y`
2444        let sym_cases = vec![
2445            (zero, zero, zero),
2446            (i1_2, i1_2, (1, 4).to_interval()),
2447            (empty, empty, empty),
2448            (invalid, invalid, empty),
2449            // ||
2450            // |-|
2451            (empty, zero, empty),
2452            (invalid, zero, empty),
2453            (empty, invalid, empty),
2454            // ||
2455            //|--|
2456            (empty, i1_2, empty),
2457            (empty, i0_10, empty),
2458            (invalid, i1_2, empty),
2459            (zero, i0_10, zero),
2460            (one, i0_10, i0_10),
2461            (i1_2, i0_10, (0, 20).to_interval()),
2462            (im5_10, i0_10, (-50, 100).to_interval()),
2463            (im5_10, im30_m20, (-300, 150).to_interval()),
2464        ];
2465
2466        for &(x, y, r) in &sym_cases {
2467            assert!(x * y == r, "{:?} * {:?} is not equal to {:?}", x, y, r);
2468            assert!(y * x == r, "{:?} * {:?} is not equal to {:?}", y, x, r);
2469        }
2470    }
2471
2472    #[test]
2473    fn test_lattice() {
2474        use gcollections::ops::lattice::test::*;
2475        use trilean::SKleene::*;
2476        let whole = Interval::<i32>::whole();
2477        let tester = LatticeTester::new(
2478            0,
2479            /* data_a */ vec![empty, empty, whole, zero, zero, zero, i1_2, i0_10, im5_5],
2480            /* data_b */ vec![zero, whole, empty, zero, one, i1_2, i0_10, im5_5, i6_10],
2481            /* a |= b*/
2482            vec![
2483                True, True, False, True, Unknown, Unknown, True, Unknown, Unknown,
2484            ],
2485            /* a |_| b */ vec![empty, empty, empty, zero, empty, empty, i1_2, i0_5, empty],
2486            /* a |-| b */ vec![zero, whole, whole, zero, i0_1, i0_2, i0_10, im5_10, im5_10],
2487        );
2488        tester.test_all();
2489    }
2490
2491    #[test]
2492    fn test_ser_de_interval() {
2493        let interval = Interval::new(10, 20);
2494        assert_tokens(
2495            &interval,
2496            &[
2497                Token::Tuple { len: 2 },
2498                Token::I32(10),
2499                Token::I32(20),
2500                Token::TupleEnd,
2501            ],
2502        );
2503    }
2504
2505    #[test]
2506    fn test_de_interval_mixed_types() {
2507        let interval = Interval::new(-5, 15);
2508        assert_de_tokens::<Interval<i32>>(
2509            &interval,
2510            &[
2511                Token::Tuple { len: 2 },
2512                Token::I32(-5),
2513                Token::I64(15),
2514                Token::TupleEnd,
2515            ],
2516        );
2517    }
2518
2519    #[test]
2520    fn test_de_interval_extra_token() {
2521        assert_de_tokens_error::<Interval<i32>>(
2522            &[
2523                Token::Tuple { len: 3 },
2524                Token::I32(10),
2525                Token::I32(20),
2526                Token::I32(30),
2527                Token::TupleEnd,
2528            ],
2529            "invalid length 3, expected tuple of two numbers or none",
2530        );
2531    }
2532
2533    #[test]
2534    fn test_de_interval_extra_tokens() {
2535        assert_de_tokens_error::<Interval<i32>>(
2536            &[
2537                Token::Tuple { len: 5 },
2538                Token::I32(10),
2539                Token::I32(20),
2540                Token::I32(30),
2541                Token::I32(40),
2542                Token::I32(50),
2543                Token::TupleEnd,
2544            ],
2545            "invalid length 5, expected tuple of two numbers or none",
2546        );
2547    }
2548
2549    #[test]
2550    fn test_ser_de_interval_u8() {
2551        let interval = Interval::<u8>::new(10, 20);
2552        assert_tokens(
2553            &interval,
2554            &[
2555                Token::Tuple { len: 2 },
2556                Token::U8(10),
2557                Token::U8(20),
2558                Token::TupleEnd,
2559            ],
2560        );
2561    }
2562
2563    #[test]
2564    fn test_ser_de_interval_i64() {
2565        let interval = Interval::<i64>::whole();
2566        assert_tokens(
2567            &interval,
2568            &[
2569                Token::Tuple { len: 2 },
2570                Token::I64(<i64 as Width>::min_value()),
2571                Token::I64(<i64 as Width>::max_value()),
2572                Token::TupleEnd,
2573            ],
2574        );
2575    }
2576
2577    #[test]
2578    fn test_ser_de_empty_interval() {
2579        let interval = Interval::<i32>::empty();
2580        assert_tokens(&interval, &[Token::None]);
2581    }
2582
2583    #[test]
2584    fn range_inclusive_to_interval_test() {
2585        let interval = (-4..=25).to_interval();
2586        assert_eq!(&interval, &Interval::new(-4, 25));
2587    }
2588
2589    #[test]
2590    fn empty_range_inclusive_to_interval_test() {
2591        let interval = (8..=3).to_interval();
2592        assert_eq!(&interval, &Interval::empty());
2593    }
2594
2595    #[test]
2596    fn range_from_to_interval_test() {
2597        let interval = (23u8..).to_interval();
2598        assert_eq!(&interval, &Interval::new(23, 254));
2599    }
2600
2601    #[test]
2602    #[should_panic]
2603    fn range_from_u8_to_interval_edge_case_test() {
2604        let _ = (255u8..).to_interval();
2605    }
2606
2607    #[test]
2608    #[should_panic]
2609    fn range_from_i8_to_interval_edge_case_test() {
2610        let _ = (-128i8..).to_interval();
2611    }
2612
2613    #[test]
2614    fn range_to_inclusive_to_interval_test() {
2615        let interval = (..=8u8).to_interval();
2616        assert_eq!(&interval, &Interval::new(0, 8));
2617    }
2618
2619    #[test]
2620    #[should_panic]
2621    fn range_to_inclusive_u8_to_interval_edge_case_test() {
2622        let _ = (..=255u8).to_interval();
2623    }
2624
2625    #[test]
2626    #[should_panic]
2627    fn range_to_inclusive_i8_to_interval_edge_case_test() {
2628        let _ = (..=-128i8).to_interval();
2629    }
2630}