hmath/bigint/arith/
mul.rs

1use crate::BigInt;
2
3impl BigInt {
4
5    #[must_use = "method returns a new number and does not mutate the original value"]
6    pub fn mul_bi(&self, other: &BigInt) -> Self {
7        let val = self.val.mul_ubi(&other.val);
8        let is_neg = !val.is_zero() && self.is_neg() != other.is_neg();
9 
10        let result = BigInt::from_ubi(val, is_neg);
11
12        #[cfg(test)] assert!(result.is_valid());
13
14        result
15    }
16
17    pub fn mul_bi_mut(&mut self, other: &BigInt) {
18        self.val.mul_ubi_mut(&other.val);
19        self._is_neg = !self.val.is_zero() && self.is_neg() != other.is_neg();
20        #[cfg(test)] assert!(self.is_valid());
21    }
22
23    #[must_use = "method returns a new number and does not mutate the original value"]
24    pub fn mul_i32(&self, other: i32) -> Self {
25        let val = self.val.mul_u32(other.abs() as u32);
26        let is_neg = !val.is_zero() && self.is_neg() != (other < 0);
27
28        let result = BigInt::from_ubi(val, is_neg);
29
30        #[cfg(test)] assert!(result.is_valid());
31
32        result
33    }
34
35    pub fn mul_i32_mut(&mut self, other: i32) {
36        self.val.mul_u32_mut(other.abs() as u32);
37        self._is_neg = !self.val.is_zero() && self.is_neg() != (other < 0);
38        #[cfg(test)] assert!(self.is_valid());
39    }
40
41    /// returns `self * 2^exp`
42    #[must_use = "method returns a new number and does not mutate the original value"]
43    pub fn mul_pow2(&self, exp: u32) -> Self {
44        BigInt::from_ubi(self.val.mul_pow2(exp), self.is_neg())
45    }
46
47    /// self *= 2^exp
48    pub fn mul_pow2_mut(&mut self, exp: u32) {
49        self.val.mul_pow2_mut(exp);
50    }
51}
52
53#[cfg(test)]
54mod tests {
55    use crate::BigInt;
56
57    #[test]
58    fn sign_test() {
59
60        for x in -7..8 {
61
62            for y in -7..8 {
63                let mut x1 = BigInt::from_i32(x);
64                let y1 = BigInt::from_i32(y);
65                let mut x2 = BigInt::from_i32(x);
66                let res1 = x1.mul_bi(&y1);
67                let res2 = x1.mul_i32(y);
68                let res3 = BigInt::from_i32(x * y);
69                x1.mul_bi_mut(&y1);
70                x2.mul_i32_mut(y);
71
72                assert_eq!(x1, x2);
73                assert_eq!(res1, res2);
74                assert_eq!(res2, res3);
75                assert_eq!(res1, x1);
76                assert_eq!(res2, x2);
77            }
78
79        }
80
81    }
82
83}