Skip to main content

relp_num/rational/big/
with_option.rs

1//! # Non-standard implementations
2//!
3//! Operations with specific types from this crate.
4use std::ops::Add;
5use std::ops::Mul;
6
7use crate::rational::big::Big;
8
9impl<const S: usize> Add<Option<&Big<S>>> for Big<S> {
10    type Output = Self;
11
12    #[inline]
13    fn add(self, rhs: Option<&Big<S>>) -> Self::Output {
14        match rhs {
15            None => self,
16            Some(rhs) => Add::add(self, rhs),
17        }
18    }
19}
20
21impl<const S: usize> Add<Option<&Big<S>>> for &Big<S> {
22    type Output = Big<S>;
23
24    #[inline]
25    fn add(self, rhs: Option<&Big<S>>) -> Self::Output {
26        match rhs {
27            None => self.clone(),
28            Some(rhs) => Add::add(self, rhs),
29        }
30    }
31}
32
33impl<const S: usize> Mul<Option<&Big<S>>> for Big<S> {
34    type Output = Self;
35
36    #[inline]
37    fn mul(self, rhs: Option<&Big<S>>) -> Self::Output {
38        match rhs {
39            None => num_traits::Zero::zero(),
40            Some(rhs) => Mul::mul(self, rhs),
41        }
42    }
43}
44
45impl<const S: usize> Mul<Option<&Big<S>>> for &Big<S> {
46    type Output = Big<S>;
47
48    #[inline]
49    fn mul(self, rhs: Option<&Big<S>>) -> Self::Output {
50        match rhs {
51            None => <Big<S> as num_traits::Zero>::zero(),
52            Some(rhs) => Mul::mul(self, rhs)
53        }
54    }
55}
56
57#[cfg(test)]
58mod test {
59    use std::str::FromStr;
60
61    use crate::fixed::{Binary, One};
62    use crate::rational::big::Big8;
63    use crate::RB;
64
65    #[test]
66    fn test_one() {
67        assert_eq!(RB!(0) + One, RB!(1));
68        assert_eq!(RB!(0) - One, RB!(-1));
69        assert_eq!(RB!(1) + One, RB!(2));
70        assert_eq!(RB!(-1) + One, RB!(0));
71        assert_eq!(RB!(-1) - One, RB!(-2));
72        assert_eq!(RB!(1) - One, RB!(0));
73        assert_eq!(RB!(1, 2) - One, RB!(-1, 2));
74        assert_eq!(RB!(1, 2) + One, RB!(3, 2));
75        assert_eq!(RB!(618, 648) / &One, RB!(618, 648));
76
77        let x = Big8::from_str("68498984987984986896468746354684684684968/68468465468464168545346854646").unwrap();
78        let expected = Big8::from_str("68498984988053455361937210523230031539614/68468465468464168545346854646").unwrap();
79        assert_eq!(x + One, expected);
80
81        let x = Big8::from_str("68468465468464168545346854645/68468465468464168545346854646").unwrap();
82        let expected = Big8::from_str("-1/68468465468464168545346854646").unwrap();
83        assert_eq!(x - One, expected);
84
85        let x = Big8::from_str("-6868468468468465168186546846416565994998987468465468464168545346854644/6868468468468465168186546846416565994998987468465468464168545346854645").unwrap();
86        let expected = Big8::from_str("1/6868468468468465168186546846416565994998987468465468464168545346854645").unwrap();
87        assert_eq!(x + One, expected);
88    }
89
90    #[test]
91    fn test_binary() {
92        assert_eq!(RB!(135, 6848) * Binary::Zero, RB!(0));
93        assert_eq!(RB!(135, 6848) * Binary::One, RB!(135, 6848));
94        assert_eq!(RB!(135, 6848) + Binary::One, RB!(135 + 6848, 6848));
95        assert_eq!(RB!(135, 6848) + Binary::Zero, RB!(135, 6848));
96        assert_eq!(RB!(0) + Binary::Zero, RB!(0));
97    }
98}