1 use super::{BigUint, IntDigits}; 2 3 use core::ops::{BitAnd, BitAndAssign, BitOr, BitOrAssign, BitXor, BitXorAssign}; 4 5 forward_val_val_binop!(impl BitAnd for BigUint, bitand); 6 forward_ref_val_binop!(impl BitAnd for BigUint, bitand); 7 8 // do not use forward_ref_ref_binop_commutative! for bitand so that we can 9 // clone the smaller value rather than the larger, avoiding over-allocation 10 impl BitAnd<&BigUint> for &BigUint { 11 type Output = BigUint; 12 13 #[inline] bitand(self, other: &BigUint) -> BigUint14 fn bitand(self, other: &BigUint) -> BigUint { 15 // forward to val-ref, choosing the smaller to clone 16 if self.data.len() <= other.data.len() { 17 self.clone() & other 18 } else { 19 other.clone() & self 20 } 21 } 22 } 23 24 forward_val_assign!(impl BitAndAssign for BigUint, bitand_assign); 25 26 impl BitAnd<&BigUint> for BigUint { 27 type Output = BigUint; 28 29 #[inline] bitand(mut self, other: &BigUint) -> BigUint30 fn bitand(mut self, other: &BigUint) -> BigUint { 31 self &= other; 32 self 33 } 34 } 35 impl BitAndAssign<&BigUint> for BigUint { 36 #[inline] bitand_assign(&mut self, other: &BigUint)37 fn bitand_assign(&mut self, other: &BigUint) { 38 for (ai, &bi) in self.data.iter_mut().zip(other.data.iter()) { 39 *ai &= bi; 40 } 41 self.data.truncate(other.data.len()); 42 self.normalize(); 43 } 44 } 45 46 forward_all_binop_to_val_ref_commutative!(impl BitOr for BigUint, bitor); 47 forward_val_assign!(impl BitOrAssign for BigUint, bitor_assign); 48 49 impl BitOr<&BigUint> for BigUint { 50 type Output = BigUint; 51 bitor(mut self, other: &BigUint) -> BigUint52 fn bitor(mut self, other: &BigUint) -> BigUint { 53 self |= other; 54 self 55 } 56 } 57 impl BitOrAssign<&BigUint> for BigUint { 58 #[inline] bitor_assign(&mut self, other: &BigUint)59 fn bitor_assign(&mut self, other: &BigUint) { 60 for (ai, &bi) in self.data.iter_mut().zip(other.data.iter()) { 61 *ai |= bi; 62 } 63 if other.data.len() > self.data.len() { 64 let extra = &other.data[self.data.len()..]; 65 self.data.extend(extra.iter().cloned()); 66 } 67 } 68 } 69 70 forward_all_binop_to_val_ref_commutative!(impl BitXor for BigUint, bitxor); 71 forward_val_assign!(impl BitXorAssign for BigUint, bitxor_assign); 72 73 impl BitXor<&BigUint> for BigUint { 74 type Output = BigUint; 75 bitxor(mut self, other: &BigUint) -> BigUint76 fn bitxor(mut self, other: &BigUint) -> BigUint { 77 self ^= other; 78 self 79 } 80 } 81 impl BitXorAssign<&BigUint> for BigUint { 82 #[inline] bitxor_assign(&mut self, other: &BigUint)83 fn bitxor_assign(&mut self, other: &BigUint) { 84 for (ai, &bi) in self.data.iter_mut().zip(other.data.iter()) { 85 *ai ^= bi; 86 } 87 if other.data.len() > self.data.len() { 88 let extra = &other.data[self.data.len()..]; 89 self.data.extend(extra.iter().cloned()); 90 } 91 self.normalize(); 92 } 93 } 94