twibint/bigint/ops/
bitwise.rs1use crate::traits::Digit;
2use crate::BigInt;
3use std::ops::{BitAnd, BitAndAssign, BitOr, BitOrAssign, BitXor, BitXorAssign, Not};
4
5impl<T: Digit> Not for BigInt<T> {
6 type Output = BigInt<T>;
7 fn not(mut self) -> BigInt<T> {
8 self.sign = !self.sign;
9 self -= T::ONE;
10 self
11 }
12}
13impl<T: Digit> Not for &BigInt<T> {
14 type Output = BigInt<T>;
15 fn not(self) -> BigInt<T> {
16 let mut ret = -self;
17 ret -= T::ONE;
18 ret
19 }
20}
21
22impl<T: Digit> BitXor<&BigInt<T>> for &BigInt<T> {
23 type Output = BigInt<T>;
24 fn bitxor(self, other: &BigInt<T>) -> BigInt<T> {
25 match (self.sign, other.sign) {
26 (true, true) => BigInt::<T>::from(&self.uint ^ &other.uint),
27 (false, false) => &!self ^ &!other,
28 (true, false) => !(self ^ &!other),
29 (false, true) => !(&!self ^ other),
30 }
31 }
32}
33impl<T: Digit> BitXor<&BigInt<T>> for BigInt<T> {
34 type Output = BigInt<T>;
35 fn bitxor(self, other: &BigInt<T>) -> Self::Output {
36 &self ^ other
37 }
38}
39impl<T: Digit> BitXor<BigInt<T>> for &BigInt<T> {
40 type Output = BigInt<T>;
41 fn bitxor(self, other: BigInt<T>) -> Self::Output {
42 self ^ &other
43 }
44}
45impl<T: Digit> BitXor<BigInt<T>> for BigInt<T> {
46 type Output = BigInt<T>;
47 fn bitxor(self, other: BigInt<T>) -> Self::Output {
48 &self ^ &other
49 }
50}
51impl<T: Digit> BitXor<T> for BigInt<T> {
52 type Output = BigInt<T>;
53 fn bitxor(self, other: T) -> Self::Output {
54 &self ^ BigInt::from_unsigned(other)
55 }
56}
57impl<T: Digit> BitXor<&T> for BigInt<T> {
58 type Output = BigInt<T>;
59 fn bitxor(self, other: &T) -> Self::Output {
60 &self ^ BigInt::from_unsigned(*other)
61 }
62}
63impl<T: Digit> BitXor<T> for &BigInt<T> {
64 type Output = BigInt<T>;
65 fn bitxor(self, other: T) -> Self::Output {
66 self ^ BigInt::from_unsigned(other)
67 }
68}
69impl<T: Digit> BitXor<&T> for &BigInt<T> {
70 type Output = BigInt<T>;
71 fn bitxor(self, other: &T) -> Self::Output {
72 self ^ BigInt::from_unsigned(*other)
73 }
74}
75impl<T: Digit> BitXorAssign<&BigInt<T>> for BigInt<T> {
76 fn bitxor_assign(&mut self, other: &BigInt<T>) {
77 *self = &*self ^ other;
78 }
79}
80impl<T: Digit> BitXorAssign<BigInt<T>> for BigInt<T> {
81 fn bitxor_assign(&mut self, other: BigInt<T>) {
82 *self = &*self ^ &other;
83 }
84}
85impl<T: Digit> BitXorAssign<T> for BigInt<T> {
86 fn bitxor_assign(&mut self, other: T) {
87 *self = &*self ^ BigInt::from_unsigned(other);
88 }
89}
90impl<T: Digit> BitXorAssign<&T> for BigInt<T> {
91 fn bitxor_assign(&mut self, other: &T) {
92 *self = &*self ^ BigInt::from_unsigned(*other);
93 }
94}
95
96impl<T: Digit> BitAnd<&BigInt<T>> for &BigInt<T> {
97 type Output = BigInt<T>;
98 fn bitand(self, other: &BigInt<T>) -> BigInt<T> {
99 match (self.sign, other.sign) {
100 (true, true) => BigInt::<T>::from(&self.uint & &other.uint),
101 (false, false) => !(&!self | &!other),
102 (true, false) => &(self ^ &!other) & self,
103 (false, true) => &(&!self ^ other) & other,
104 }
105 }
106}
107impl<T: Digit> BitAnd<BigInt<T>> for BigInt<T> {
108 type Output = BigInt<T>;
109 fn bitand(self, other: BigInt<T>) -> Self::Output {
110 &self & &other
111 }
112}
113impl<T: Digit> BitAnd<&BigInt<T>> for BigInt<T> {
114 type Output = BigInt<T>;
115 fn bitand(self, other: &BigInt<T>) -> Self::Output {
116 &self & other
117 }
118}
119impl<T: Digit> BitAnd<BigInt<T>> for &BigInt<T> {
120 type Output = BigInt<T>;
121 fn bitand(self, other: BigInt<T>) -> Self::Output {
122 self & &other
123 }
124}
125impl<T: Digit> BitAndAssign<&BigInt<T>> for BigInt<T> {
126 fn bitand_assign(&mut self, other: &BigInt<T>) {
127 *self = &*self & other;
128 }
129}
130impl<T: Digit> BitAndAssign<BigInt<T>> for BigInt<T> {
131 fn bitand_assign(&mut self, other: BigInt<T>) {
132 *self = &*self & &other;
133 }
134}
135impl<T: Digit> BitAndAssign<T> for BigInt<T> {
136 fn bitand_assign(&mut self, other: T) {
137 *self = &*self & BigInt::<T>::from_unsigned(other);
138 }
139}
140impl<T: Digit> BitAndAssign<&T> for BigInt<T> {
141 fn bitand_assign(&mut self, other: &T) {
142 *self = &*self & BigInt::<T>::from_unsigned(*other);
143 }
144}
145impl<T: Digit> BitAnd<T> for BigInt<T> {
146 type Output = BigInt<T>;
147 fn bitand(mut self, other: T) -> Self::Output {
148 self &= other;
149 self
150 }
151}
152impl<T: Digit> BitAnd<&T> for BigInt<T> {
153 type Output = BigInt<T>;
154 fn bitand(mut self, other: &T) -> Self::Output {
155 self &= other;
156 self
157 }
158}
159impl<T: Digit> BitAnd<T> for &BigInt<T> {
160 type Output = BigInt<T>;
161 fn bitand(self, other: T) -> Self::Output {
162 let mut ret = self.clone();
163 ret &= other;
164 ret
165 }
166}
167impl<T: Digit> BitAnd<&T> for &BigInt<T> {
168 type Output = BigInt<T>;
169 fn bitand(self, other: &T) -> Self::Output {
170 let mut ret = self.clone();
171 ret &= other;
172 ret
173 }
174}
175
176impl<T: Digit> BitOr<&BigInt<T>> for &BigInt<T> {
177 type Output = BigInt<T>;
178 fn bitor(self, other: &BigInt<T>) -> BigInt<T> {
179 match (self.sign, other.sign) {
180 (true, true) => BigInt::<T>::from(&self.uint | &other.uint),
181 _ => !(&!self & &!other),
182 }
183 }
184}
185impl<T: Digit> BitOr<BigInt<T>> for &BigInt<T> {
186 type Output = BigInt<T>;
187 fn bitor(self, other: BigInt<T>) -> Self::Output {
188 self | &other
189 }
190}
191impl<T: Digit> BitOr<&BigInt<T>> for BigInt<T> {
192 type Output = BigInt<T>;
193 fn bitor(self, other: &BigInt<T>) -> Self::Output {
194 &self | other
195 }
196}
197impl<T: Digit> BitOr<BigInt<T>> for BigInt<T> {
198 type Output = BigInt<T>;
199 fn bitor(self, other: BigInt<T>) -> Self::Output {
200 &self | &other
201 }
202}
203impl<T: Digit> BitOr<T> for BigInt<T> {
204 type Output = BigInt<T>;
205 fn bitor(self, other: T) -> Self::Output {
206 &self | BigInt::from_unsigned(other)
207 }
208}
209impl<T: Digit> BitOr<T> for &BigInt<T> {
210 type Output = BigInt<T>;
211 fn bitor(self, other: T) -> Self::Output {
212 self | BigInt::from_unsigned(other)
213 }
214}
215impl<T: Digit> BitOr<&T> for BigInt<T> {
216 type Output = BigInt<T>;
217 fn bitor(self, other: &T) -> Self::Output {
218 &self | BigInt::from_unsigned(*other)
219 }
220}
221impl<T: Digit> BitOr<&T> for &BigInt<T> {
222 type Output = BigInt<T>;
223 fn bitor(self, other: &T) -> Self::Output {
224 self | BigInt::from_unsigned(*other)
225 }
226}
227impl<T: Digit> BitOrAssign<&BigInt<T>> for BigInt<T> {
228 fn bitor_assign(&mut self, other: &BigInt<T>) {
229 *self = &*self | other;
230 }
231}
232impl<T: Digit> BitOrAssign<BigInt<T>> for BigInt<T> {
233 fn bitor_assign(&mut self, other: BigInt<T>) {
234 *self = &*self | &other;
235 }
236}
237impl<T: Digit> BitOrAssign<T> for BigInt<T> {
238 fn bitor_assign(&mut self, other: T) {
239 *self = &*self | BigInt::from_unsigned(other);
240 }
241}
242impl<T: Digit> BitOrAssign<&T> for BigInt<T> {
243 fn bitor_assign(&mut self, other: &T) {
244 *self = &*self | BigInt::from_unsigned(*other);
245 }
246}