1 | //! Type-level signed integers. |
2 | //! |
3 | //! |
4 | //! Type **operators** implemented: |
5 | //! |
6 | //! From `core::ops`: `Add`, `Sub`, `Mul`, `Div`, and `Rem`. |
7 | //! From `typenum`: `Same`, `Cmp`, and `Pow`. |
8 | //! |
9 | //! Rather than directly using the structs defined in this module, it is recommended that |
10 | //! you import and use the relevant aliases from the [consts](../consts/index.html) module. |
11 | //! |
12 | //! Note that operators that work on the underlying structure of the number are |
13 | //! intentionally not implemented. This is because this implementation of signed integers |
14 | //! does *not* use twos-complement, and implementing them would require making arbitrary |
15 | //! choices, causing the results of such operators to be difficult to reason about. |
16 | //! |
17 | //! # Example |
18 | //! ```rust |
19 | //! use std::ops::{Add, Div, Mul, Rem, Sub}; |
20 | //! use typenum::{Integer, N3, P2}; |
21 | //! |
22 | //! assert_eq!(<N3 as Add<P2>>::Output::to_i32(), -1); |
23 | //! assert_eq!(<N3 as Sub<P2>>::Output::to_i32(), -5); |
24 | //! assert_eq!(<N3 as Mul<P2>>::Output::to_i32(), -6); |
25 | //! assert_eq!(<N3 as Div<P2>>::Output::to_i32(), -1); |
26 | //! assert_eq!(<N3 as Rem<P2>>::Output::to_i32(), -1); |
27 | //! ``` |
28 | |
29 | pub use crate::marker_traits::Integer; |
30 | use crate::{ |
31 | bit::{Bit, B0, B1}, |
32 | consts::{N1, P1, U0, U1}, |
33 | private::{Internal, InternalMarker, PrivateDivInt, PrivateIntegerAdd, PrivateRem}, |
34 | uint::{UInt, Unsigned}, |
35 | Cmp, Equal, Greater, Less, NonZero, Pow, PowerOfTwo, ToInt, Zero, |
36 | }; |
37 | use core::ops::{Add, Div, Mul, Neg, Rem, Sub}; |
38 | |
39 | /// Type-level signed integers with positive sign. |
40 | #[derive (Eq, PartialEq, Ord, PartialOrd, Clone, Copy, Hash, Debug, Default)] |
41 | #[cfg_attr (feature = "scale_info" , derive(scale_info::TypeInfo))] |
42 | pub struct PInt<U: Unsigned + NonZero> { |
43 | pub(crate) n: U, |
44 | } |
45 | |
46 | /// Type-level signed integers with negative sign. |
47 | #[derive (Eq, PartialEq, Ord, PartialOrd, Clone, Copy, Hash, Debug, Default)] |
48 | #[cfg_attr (feature = "scale_info" , derive(scale_info::TypeInfo))] |
49 | pub struct NInt<U: Unsigned + NonZero> { |
50 | pub(crate) n: U, |
51 | } |
52 | |
53 | impl<U: Unsigned + NonZero> PInt<U> { |
54 | /// Instantiates a singleton representing this strictly positive integer. |
55 | #[inline ] |
56 | pub fn new() -> PInt<U> { |
57 | PInt::default() |
58 | } |
59 | } |
60 | |
61 | impl<U: Unsigned + NonZero> NInt<U> { |
62 | /// Instantiates a singleton representing this strictly negative integer. |
63 | #[inline ] |
64 | pub fn new() -> NInt<U> { |
65 | NInt::default() |
66 | } |
67 | } |
68 | |
69 | /// The type-level signed integer 0. |
70 | #[derive (Eq, PartialEq, Ord, PartialOrd, Clone, Copy, Hash, Debug, Default)] |
71 | #[cfg_attr (feature = "scale_info" , derive(scale_info::TypeInfo))] |
72 | pub struct Z0; |
73 | |
74 | impl Z0 { |
75 | /// Instantiates a singleton representing the integer 0. |
76 | #[inline ] |
77 | pub fn new() -> Z0 { |
78 | Z0 |
79 | } |
80 | } |
81 | |
82 | impl<U: Unsigned + NonZero> NonZero for PInt<U> {} |
83 | impl<U: Unsigned + NonZero> NonZero for NInt<U> {} |
84 | impl Zero for Z0 {} |
85 | |
86 | impl<U: Unsigned + NonZero + PowerOfTwo> PowerOfTwo for PInt<U> {} |
87 | |
88 | impl Integer for Z0 { |
89 | const I8: i8 = 0; |
90 | const I16: i16 = 0; |
91 | const I32: i32 = 0; |
92 | const I64: i64 = 0; |
93 | #[cfg (feature = "i128" )] |
94 | const I128: i128 = 0; |
95 | const ISIZE: isize = 0; |
96 | |
97 | #[inline ] |
98 | fn to_i8() -> i8 { |
99 | 0 |
100 | } |
101 | #[inline ] |
102 | fn to_i16() -> i16 { |
103 | 0 |
104 | } |
105 | #[inline ] |
106 | fn to_i32() -> i32 { |
107 | 0 |
108 | } |
109 | #[inline ] |
110 | fn to_i64() -> i64 { |
111 | 0 |
112 | } |
113 | #[cfg (feature = "i128" )] |
114 | #[inline ] |
115 | fn to_i128() -> i128 { |
116 | 0 |
117 | } |
118 | #[inline ] |
119 | fn to_isize() -> isize { |
120 | 0 |
121 | } |
122 | } |
123 | |
124 | impl<U: Unsigned + NonZero> Integer for PInt<U> { |
125 | const I8: i8 = U::I8; |
126 | const I16: i16 = U::I16; |
127 | const I32: i32 = U::I32; |
128 | const I64: i64 = U::I64; |
129 | #[cfg (feature = "i128" )] |
130 | const I128: i128 = U::I128; |
131 | const ISIZE: isize = U::ISIZE; |
132 | |
133 | #[inline ] |
134 | fn to_i8() -> i8 { |
135 | <U as Unsigned>::to_i8() |
136 | } |
137 | #[inline ] |
138 | fn to_i16() -> i16 { |
139 | <U as Unsigned>::to_i16() |
140 | } |
141 | #[inline ] |
142 | fn to_i32() -> i32 { |
143 | <U as Unsigned>::to_i32() |
144 | } |
145 | #[inline ] |
146 | fn to_i64() -> i64 { |
147 | <U as Unsigned>::to_i64() |
148 | } |
149 | #[cfg (feature = "i128" )] |
150 | #[inline ] |
151 | fn to_i128() -> i128 { |
152 | <U as Unsigned>::to_i128() |
153 | } |
154 | #[inline ] |
155 | fn to_isize() -> isize { |
156 | <U as Unsigned>::to_isize() |
157 | } |
158 | } |
159 | |
160 | // Simply negating the result of e.g. `U::I8` will result in overflow for `std::i8::MIN`. Instead, |
161 | // we use the fact that `U: NonZero` by subtracting one from the `U::U8` before negating. |
162 | impl<U: Unsigned + NonZero> Integer for NInt<U> { |
163 | const I8: i8 = -((U::U8 - 1) as i8) - 1; |
164 | const I16: i16 = -((U::U16 - 1) as i16) - 1; |
165 | const I32: i32 = -((U::U32 - 1) as i32) - 1; |
166 | const I64: i64 = -((U::U64 - 1) as i64) - 1; |
167 | #[cfg (feature = "i128" )] |
168 | const I128: i128 = -((U::U128 - 1) as i128) - 1; |
169 | const ISIZE: isize = -((U::USIZE - 1) as isize) - 1; |
170 | |
171 | #[inline ] |
172 | fn to_i8() -> i8 { |
173 | Self::I8 |
174 | } |
175 | #[inline ] |
176 | fn to_i16() -> i16 { |
177 | Self::I16 |
178 | } |
179 | #[inline ] |
180 | fn to_i32() -> i32 { |
181 | Self::I32 |
182 | } |
183 | #[inline ] |
184 | fn to_i64() -> i64 { |
185 | Self::I64 |
186 | } |
187 | #[cfg (feature = "i128" )] |
188 | #[inline ] |
189 | fn to_i128() -> i128 { |
190 | Self::I128 |
191 | } |
192 | #[inline ] |
193 | fn to_isize() -> isize { |
194 | Self::ISIZE |
195 | } |
196 | } |
197 | |
198 | // --------------------------------------------------------------------------------------- |
199 | // Neg |
200 | |
201 | /// `-Z0 = Z0` |
202 | impl Neg for Z0 { |
203 | type Output = Z0; |
204 | #[inline ] |
205 | fn neg(self) -> Self::Output { |
206 | Z0 |
207 | } |
208 | } |
209 | |
210 | /// `-PInt = NInt` |
211 | impl<U: Unsigned + NonZero> Neg for PInt<U> { |
212 | type Output = NInt<U>; |
213 | #[inline ] |
214 | fn neg(self) -> Self::Output { |
215 | NInt::new() |
216 | } |
217 | } |
218 | |
219 | /// `-NInt = PInt` |
220 | impl<U: Unsigned + NonZero> Neg for NInt<U> { |
221 | type Output = PInt<U>; |
222 | #[inline ] |
223 | fn neg(self) -> Self::Output { |
224 | PInt::new() |
225 | } |
226 | } |
227 | |
228 | // --------------------------------------------------------------------------------------- |
229 | // Add |
230 | |
231 | /// `Z0 + I = I` |
232 | impl<I: Integer> Add<I> for Z0 { |
233 | type Output = I; |
234 | #[inline ] |
235 | fn add(self, rhs: I) -> Self::Output { |
236 | rhs |
237 | } |
238 | } |
239 | |
240 | /// `PInt + Z0 = PInt` |
241 | impl<U: Unsigned + NonZero> Add<Z0> for PInt<U> { |
242 | type Output = PInt<U>; |
243 | #[inline ] |
244 | fn add(self, _: Z0) -> Self::Output { |
245 | PInt::new() |
246 | } |
247 | } |
248 | |
249 | /// `NInt + Z0 = NInt` |
250 | impl<U: Unsigned + NonZero> Add<Z0> for NInt<U> { |
251 | type Output = NInt<U>; |
252 | #[inline ] |
253 | fn add(self, _: Z0) -> Self::Output { |
254 | NInt::new() |
255 | } |
256 | } |
257 | |
258 | /// `P(Ul) + P(Ur) = P(Ul + Ur)` |
259 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Add<PInt<Ur>> for PInt<Ul> |
260 | where |
261 | Ul: Add<Ur>, |
262 | <Ul as Add<Ur>>::Output: Unsigned + NonZero, |
263 | { |
264 | type Output = PInt<<Ul as Add<Ur>>::Output>; |
265 | #[inline ] |
266 | fn add(self, _: PInt<Ur>) -> Self::Output { |
267 | PInt::new() |
268 | } |
269 | } |
270 | |
271 | /// `N(Ul) + N(Ur) = N(Ul + Ur)` |
272 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Add<NInt<Ur>> for NInt<Ul> |
273 | where |
274 | Ul: Add<Ur>, |
275 | <Ul as Add<Ur>>::Output: Unsigned + NonZero, |
276 | { |
277 | type Output = NInt<<Ul as Add<Ur>>::Output>; |
278 | #[inline ] |
279 | fn add(self, _: NInt<Ur>) -> Self::Output { |
280 | NInt::new() |
281 | } |
282 | } |
283 | |
284 | /// `P(Ul) + N(Ur)`: We resolve this with our `PrivateAdd` |
285 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Add<NInt<Ur>> for PInt<Ul> |
286 | where |
287 | Ul: Cmp<Ur> + PrivateIntegerAdd<<Ul as Cmp<Ur>>::Output, Ur>, |
288 | { |
289 | type Output = <Ul as PrivateIntegerAdd<<Ul as Cmp<Ur>>::Output, Ur>>::Output; |
290 | #[inline ] |
291 | fn add(self, rhs: NInt<Ur>) -> Self::Output { |
292 | let lhs: Ul = self.n; |
293 | let rhs: Ur = rhs.n; |
294 | let lhs_cmp_rhs: = lhs.compare::<Internal>(&rhs); |
295 | lhs.private_integer_add(lhs_cmp_rhs, rhs) |
296 | } |
297 | } |
298 | |
299 | /// `N(Ul) + P(Ur)`: We resolve this with our `PrivateAdd` |
300 | // We just do the same thing as above, swapping Lhs and Rhs |
301 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Add<PInt<Ur>> for NInt<Ul> |
302 | where |
303 | Ur: Cmp<Ul> + PrivateIntegerAdd<<Ur as Cmp<Ul>>::Output, Ul>, |
304 | { |
305 | type Output = <Ur as PrivateIntegerAdd<<Ur as Cmp<Ul>>::Output, Ul>>::Output; |
306 | #[inline ] |
307 | fn add(self, rhs: PInt<Ur>) -> Self::Output { |
308 | let lhs: Ul = self.n; |
309 | let rhs: Ur = rhs.n; |
310 | let rhs_cmp_lhs: >::Output = rhs.compare::<Internal>(&lhs); |
311 | rhs.private_integer_add(rhs_cmp_lhs, lhs) |
312 | } |
313 | } |
314 | |
315 | /// `P + N = 0` where `P == N` |
316 | impl<N: Unsigned, P: Unsigned> PrivateIntegerAdd<Equal, N> for P { |
317 | type Output = Z0; |
318 | |
319 | #[inline ] |
320 | fn private_integer_add(self, _: Equal, _: N) -> Self::Output { |
321 | Z0 |
322 | } |
323 | } |
324 | |
325 | /// `P + N = Positive` where `P > N` |
326 | impl<N: Unsigned, P: Unsigned> PrivateIntegerAdd<Greater, N> for P |
327 | where |
328 | P: Sub<N>, |
329 | <P as Sub<N>>::Output: Unsigned + NonZero, |
330 | { |
331 | type Output = PInt<<P as Sub<N>>::Output>; |
332 | |
333 | #[inline ] |
334 | fn private_integer_add(self, _: Greater, n: N) -> Self::Output { |
335 | PInt { n: self - n } |
336 | } |
337 | } |
338 | |
339 | /// `P + N = Negative` where `P < N` |
340 | impl<N: Unsigned, P: Unsigned> PrivateIntegerAdd<Less, N> for P |
341 | where |
342 | N: Sub<P>, |
343 | <N as Sub<P>>::Output: Unsigned + NonZero, |
344 | { |
345 | type Output = NInt<<N as Sub<P>>::Output>; |
346 | |
347 | #[inline ] |
348 | fn private_integer_add(self, _: Less, n: N) -> Self::Output { |
349 | NInt { n: n - self } |
350 | } |
351 | } |
352 | |
353 | // --------------------------------------------------------------------------------------- |
354 | // Sub |
355 | |
356 | /// `Z0 - Z0 = Z0` |
357 | impl Sub<Z0> for Z0 { |
358 | type Output = Z0; |
359 | #[inline ] |
360 | fn sub(self, _: Z0) -> Self::Output { |
361 | Z0 |
362 | } |
363 | } |
364 | |
365 | /// `Z0 - P = N` |
366 | impl<U: Unsigned + NonZero> Sub<PInt<U>> for Z0 { |
367 | type Output = NInt<U>; |
368 | #[inline ] |
369 | fn sub(self, _: PInt<U>) -> Self::Output { |
370 | NInt::new() |
371 | } |
372 | } |
373 | |
374 | /// `Z0 - N = P` |
375 | impl<U: Unsigned + NonZero> Sub<NInt<U>> for Z0 { |
376 | type Output = PInt<U>; |
377 | #[inline ] |
378 | fn sub(self, _: NInt<U>) -> Self::Output { |
379 | PInt::new() |
380 | } |
381 | } |
382 | |
383 | /// `PInt - Z0 = PInt` |
384 | impl<U: Unsigned + NonZero> Sub<Z0> for PInt<U> { |
385 | type Output = PInt<U>; |
386 | #[inline ] |
387 | fn sub(self, _: Z0) -> Self::Output { |
388 | PInt::new() |
389 | } |
390 | } |
391 | |
392 | /// `NInt - Z0 = NInt` |
393 | impl<U: Unsigned + NonZero> Sub<Z0> for NInt<U> { |
394 | type Output = NInt<U>; |
395 | #[inline ] |
396 | fn sub(self, _: Z0) -> Self::Output { |
397 | NInt::new() |
398 | } |
399 | } |
400 | |
401 | /// `P(Ul) - N(Ur) = P(Ul + Ur)` |
402 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Sub<NInt<Ur>> for PInt<Ul> |
403 | where |
404 | Ul: Add<Ur>, |
405 | <Ul as Add<Ur>>::Output: Unsigned + NonZero, |
406 | { |
407 | type Output = PInt<<Ul as Add<Ur>>::Output>; |
408 | #[inline ] |
409 | fn sub(self, _: NInt<Ur>) -> Self::Output { |
410 | PInt::new() |
411 | } |
412 | } |
413 | |
414 | /// `N(Ul) - P(Ur) = N(Ul + Ur)` |
415 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Sub<PInt<Ur>> for NInt<Ul> |
416 | where |
417 | Ul: Add<Ur>, |
418 | <Ul as Add<Ur>>::Output: Unsigned + NonZero, |
419 | { |
420 | type Output = NInt<<Ul as Add<Ur>>::Output>; |
421 | #[inline ] |
422 | fn sub(self, _: PInt<Ur>) -> Self::Output { |
423 | NInt::new() |
424 | } |
425 | } |
426 | |
427 | /// `P(Ul) - P(Ur)`: We resolve this with our `PrivateAdd` |
428 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Sub<PInt<Ur>> for PInt<Ul> |
429 | where |
430 | Ul: Cmp<Ur> + PrivateIntegerAdd<<Ul as Cmp<Ur>>::Output, Ur>, |
431 | { |
432 | type Output = <Ul as PrivateIntegerAdd<<Ul as Cmp<Ur>>::Output, Ur>>::Output; |
433 | #[inline ] |
434 | fn sub(self, rhs: PInt<Ur>) -> Self::Output { |
435 | let lhs: Ul = self.n; |
436 | let rhs: Ur = rhs.n; |
437 | let lhs_cmp_rhs: = lhs.compare::<Internal>(&rhs); |
438 | lhs.private_integer_add(lhs_cmp_rhs, rhs) |
439 | } |
440 | } |
441 | |
442 | /// `N(Ul) - N(Ur)`: We resolve this with our `PrivateAdd` |
443 | // We just do the same thing as above, swapping Lhs and Rhs |
444 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Sub<NInt<Ur>> for NInt<Ul> |
445 | where |
446 | Ur: Cmp<Ul> + PrivateIntegerAdd<<Ur as Cmp<Ul>>::Output, Ul>, |
447 | { |
448 | type Output = <Ur as PrivateIntegerAdd<<Ur as Cmp<Ul>>::Output, Ul>>::Output; |
449 | #[inline ] |
450 | fn sub(self, rhs: NInt<Ur>) -> Self::Output { |
451 | let lhs: Ul = self.n; |
452 | let rhs: Ur = rhs.n; |
453 | let rhs_cmp_lhs: >::Output = rhs.compare::<Internal>(&lhs); |
454 | rhs.private_integer_add(rhs_cmp_lhs, lhs) |
455 | } |
456 | } |
457 | |
458 | // --------------------------------------------------------------------------------------- |
459 | // Mul |
460 | |
461 | /// `Z0 * I = Z0` |
462 | impl<I: Integer> Mul<I> for Z0 { |
463 | type Output = Z0; |
464 | #[inline ] |
465 | fn mul(self, _: I) -> Self::Output { |
466 | Z0 |
467 | } |
468 | } |
469 | |
470 | /// `P * Z0 = Z0` |
471 | impl<U: Unsigned + NonZero> Mul<Z0> for PInt<U> { |
472 | type Output = Z0; |
473 | #[inline ] |
474 | fn mul(self, _: Z0) -> Self::Output { |
475 | Z0 |
476 | } |
477 | } |
478 | |
479 | /// `N * Z0 = Z0` |
480 | impl<U: Unsigned + NonZero> Mul<Z0> for NInt<U> { |
481 | type Output = Z0; |
482 | #[inline ] |
483 | fn mul(self, _: Z0) -> Self::Output { |
484 | Z0 |
485 | } |
486 | } |
487 | |
488 | /// P(Ul) * P(Ur) = P(Ul * Ur) |
489 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Mul<PInt<Ur>> for PInt<Ul> |
490 | where |
491 | Ul: Mul<Ur>, |
492 | <Ul as Mul<Ur>>::Output: Unsigned + NonZero, |
493 | { |
494 | type Output = PInt<<Ul as Mul<Ur>>::Output>; |
495 | #[inline ] |
496 | fn mul(self, _: PInt<Ur>) -> Self::Output { |
497 | PInt::new() |
498 | } |
499 | } |
500 | |
501 | /// N(Ul) * N(Ur) = P(Ul * Ur) |
502 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Mul<NInt<Ur>> for NInt<Ul> |
503 | where |
504 | Ul: Mul<Ur>, |
505 | <Ul as Mul<Ur>>::Output: Unsigned + NonZero, |
506 | { |
507 | type Output = PInt<<Ul as Mul<Ur>>::Output>; |
508 | #[inline ] |
509 | fn mul(self, _: NInt<Ur>) -> Self::Output { |
510 | PInt::new() |
511 | } |
512 | } |
513 | |
514 | /// P(Ul) * N(Ur) = N(Ul * Ur) |
515 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Mul<NInt<Ur>> for PInt<Ul> |
516 | where |
517 | Ul: Mul<Ur>, |
518 | <Ul as Mul<Ur>>::Output: Unsigned + NonZero, |
519 | { |
520 | type Output = NInt<<Ul as Mul<Ur>>::Output>; |
521 | #[inline ] |
522 | fn mul(self, _: NInt<Ur>) -> Self::Output { |
523 | NInt::new() |
524 | } |
525 | } |
526 | |
527 | /// N(Ul) * P(Ur) = N(Ul * Ur) |
528 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Mul<PInt<Ur>> for NInt<Ul> |
529 | where |
530 | Ul: Mul<Ur>, |
531 | <Ul as Mul<Ur>>::Output: Unsigned + NonZero, |
532 | { |
533 | type Output = NInt<<Ul as Mul<Ur>>::Output>; |
534 | #[inline ] |
535 | fn mul(self, _: PInt<Ur>) -> Self::Output { |
536 | NInt::new() |
537 | } |
538 | } |
539 | |
540 | // --------------------------------------------------------------------------------------- |
541 | // Div |
542 | |
543 | /// `Z0 / I = Z0` where `I != 0` |
544 | impl<I: Integer + NonZero> Div<I> for Z0 { |
545 | type Output = Z0; |
546 | #[inline ] |
547 | fn div(self, _: I) -> Self::Output { |
548 | Z0 |
549 | } |
550 | } |
551 | |
552 | macro_rules! impl_int_div { |
553 | ($A:ident, $B:ident, $R:ident) => { |
554 | /// `$A<Ul> / $B<Ur> = $R<Ul / Ur>` |
555 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Div<$B<Ur>> for $A<Ul> |
556 | where |
557 | Ul: Cmp<Ur>, |
558 | $A<Ul>: PrivateDivInt<<Ul as Cmp<Ur>>::Output, $B<Ur>>, |
559 | { |
560 | type Output = <$A<Ul> as PrivateDivInt<<Ul as Cmp<Ur>>::Output, $B<Ur>>>::Output; |
561 | #[inline] |
562 | fn div(self, rhs: $B<Ur>) -> Self::Output { |
563 | let lhs_cmp_rhs = self.n.compare::<Internal>(&rhs.n); |
564 | self.private_div_int(lhs_cmp_rhs, rhs) |
565 | } |
566 | } |
567 | impl<Ul, Ur> PrivateDivInt<Less, $B<Ur>> for $A<Ul> |
568 | where |
569 | Ul: Unsigned + NonZero, |
570 | Ur: Unsigned + NonZero, |
571 | { |
572 | type Output = Z0; |
573 | |
574 | #[inline] |
575 | fn private_div_int(self, _: Less, _: $B<Ur>) -> Self::Output { |
576 | Z0 |
577 | } |
578 | } |
579 | impl<Ul, Ur> PrivateDivInt<Equal, $B<Ur>> for $A<Ul> |
580 | where |
581 | Ul: Unsigned + NonZero, |
582 | Ur: Unsigned + NonZero, |
583 | { |
584 | type Output = $R<U1>; |
585 | |
586 | #[inline] |
587 | fn private_div_int(self, _: Equal, _: $B<Ur>) -> Self::Output { |
588 | $R { n: U1::new() } |
589 | } |
590 | } |
591 | impl<Ul, Ur> PrivateDivInt<Greater, $B<Ur>> for $A<Ul> |
592 | where |
593 | Ul: Unsigned + NonZero + Div<Ur>, |
594 | Ur: Unsigned + NonZero, |
595 | <Ul as Div<Ur>>::Output: Unsigned + NonZero, |
596 | { |
597 | type Output = $R<<Ul as Div<Ur>>::Output>; |
598 | |
599 | #[inline] |
600 | fn private_div_int(self, _: Greater, d: $B<Ur>) -> Self::Output { |
601 | $R { n: self.n / d.n } |
602 | } |
603 | } |
604 | }; |
605 | } |
606 | |
607 | impl_int_div!(PInt, PInt, PInt); |
608 | impl_int_div!(PInt, NInt, NInt); |
609 | impl_int_div!(NInt, PInt, NInt); |
610 | impl_int_div!(NInt, NInt, PInt); |
611 | |
612 | // --------------------------------------------------------------------------------------- |
613 | // PartialDiv |
614 | |
615 | use crate::{PartialDiv, Quot}; |
616 | |
617 | impl<M, N> PartialDiv<N> for M |
618 | where |
619 | M: Integer + Div<N> + Rem<N, Output = Z0>, |
620 | { |
621 | type Output = Quot<M, N>; |
622 | #[inline ] |
623 | fn partial_div(self, rhs: N) -> Self::Output { |
624 | self / rhs |
625 | } |
626 | } |
627 | |
628 | // --------------------------------------------------------------------------------------- |
629 | // Cmp |
630 | |
631 | /// 0 == 0 |
632 | impl Cmp<Z0> for Z0 { |
633 | type Output = Equal; |
634 | |
635 | #[inline ] |
636 | fn compare<IM: InternalMarker>(&self, _: &Z0) -> Self::Output { |
637 | Equal |
638 | } |
639 | } |
640 | |
641 | /// 0 > -X |
642 | impl<U: Unsigned + NonZero> Cmp<NInt<U>> for Z0 { |
643 | type Output = Greater; |
644 | |
645 | #[inline ] |
646 | fn compare<IM: InternalMarker>(&self, _: &NInt<U>) -> Self::Output { |
647 | Greater |
648 | } |
649 | } |
650 | |
651 | /// 0 < X |
652 | impl<U: Unsigned + NonZero> Cmp<PInt<U>> for Z0 { |
653 | type Output = Less; |
654 | |
655 | #[inline ] |
656 | fn compare<IM: InternalMarker>(&self, _: &PInt<U>) -> Self::Output { |
657 | Less |
658 | } |
659 | } |
660 | |
661 | /// X > 0 |
662 | impl<U: Unsigned + NonZero> Cmp<Z0> for PInt<U> { |
663 | type Output = Greater; |
664 | |
665 | #[inline ] |
666 | fn compare<IM: InternalMarker>(&self, _: &Z0) -> Self::Output { |
667 | Greater |
668 | } |
669 | } |
670 | |
671 | /// -X < 0 |
672 | impl<U: Unsigned + NonZero> Cmp<Z0> for NInt<U> { |
673 | type Output = Less; |
674 | |
675 | #[inline ] |
676 | fn compare<IM: InternalMarker>(&self, _: &Z0) -> Self::Output { |
677 | Less |
678 | } |
679 | } |
680 | |
681 | /// -X < Y |
682 | impl<P: Unsigned + NonZero, N: Unsigned + NonZero> Cmp<PInt<P>> for NInt<N> { |
683 | type Output = Less; |
684 | |
685 | #[inline ] |
686 | fn compare<IM: InternalMarker>(&self, _: &PInt<P>) -> Self::Output { |
687 | Less |
688 | } |
689 | } |
690 | |
691 | /// X > - Y |
692 | impl<P: Unsigned + NonZero, N: Unsigned + NonZero> Cmp<NInt<N>> for PInt<P> { |
693 | type Output = Greater; |
694 | |
695 | #[inline ] |
696 | fn compare<IM: InternalMarker>(&self, _: &NInt<N>) -> Self::Output { |
697 | Greater |
698 | } |
699 | } |
700 | |
701 | /// X <==> Y |
702 | impl<Pl: Cmp<Pr> + Unsigned + NonZero, Pr: Unsigned + NonZero> Cmp<PInt<Pr>> for PInt<Pl> { |
703 | type Output = <Pl as Cmp<Pr>>::Output; |
704 | |
705 | #[inline ] |
706 | fn compare<IM: InternalMarker>(&self, rhs: &PInt<Pr>) -> Self::Output { |
707 | self.n.compare::<Internal>(&rhs.n) |
708 | } |
709 | } |
710 | |
711 | /// -X <==> -Y |
712 | impl<Nl: Unsigned + NonZero, Nr: Cmp<Nl> + Unsigned + NonZero> Cmp<NInt<Nr>> for NInt<Nl> { |
713 | type Output = <Nr as Cmp<Nl>>::Output; |
714 | |
715 | #[inline ] |
716 | fn compare<IM: InternalMarker>(&self, rhs: &NInt<Nr>) -> Self::Output { |
717 | rhs.n.compare::<Internal>(&self.n) |
718 | } |
719 | } |
720 | |
721 | // --------------------------------------------------------------------------------------- |
722 | // Rem |
723 | |
724 | /// `Z0 % I = Z0` where `I != 0` |
725 | impl<I: Integer + NonZero> Rem<I> for Z0 { |
726 | type Output = Z0; |
727 | #[inline ] |
728 | fn rem(self, _: I) -> Self::Output { |
729 | Z0 |
730 | } |
731 | } |
732 | |
733 | macro_rules! impl_int_rem { |
734 | ($A:ident, $B:ident, $R:ident) => { |
735 | /// `$A<Ul> % $B<Ur> = $R<Ul % Ur>` |
736 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Rem<$B<Ur>> for $A<Ul> |
737 | where |
738 | Ul: Rem<Ur>, |
739 | $A<Ul>: PrivateRem<<Ul as Rem<Ur>>::Output, $B<Ur>>, |
740 | { |
741 | type Output = <$A<Ul> as PrivateRem<<Ul as Rem<Ur>>::Output, $B<Ur>>>::Output; |
742 | #[inline] |
743 | fn rem(self, rhs: $B<Ur>) -> Self::Output { |
744 | self.private_rem(self.n % rhs.n, rhs) |
745 | } |
746 | } |
747 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> PrivateRem<U0, $B<Ur>> for $A<Ul> { |
748 | type Output = Z0; |
749 | |
750 | #[inline] |
751 | fn private_rem(self, _: U0, _: $B<Ur>) -> Self::Output { |
752 | Z0 |
753 | } |
754 | } |
755 | impl<Ul, Ur, U, B> PrivateRem<UInt<U, B>, $B<Ur>> for $A<Ul> |
756 | where |
757 | Ul: Unsigned + NonZero, |
758 | Ur: Unsigned + NonZero, |
759 | U: Unsigned, |
760 | B: Bit, |
761 | { |
762 | type Output = $R<UInt<U, B>>; |
763 | |
764 | #[inline] |
765 | fn private_rem(self, urem: UInt<U, B>, _: $B<Ur>) -> Self::Output { |
766 | $R { n: urem } |
767 | } |
768 | } |
769 | }; |
770 | } |
771 | |
772 | impl_int_rem!(PInt, PInt, PInt); |
773 | impl_int_rem!(PInt, NInt, PInt); |
774 | impl_int_rem!(NInt, PInt, NInt); |
775 | impl_int_rem!(NInt, NInt, NInt); |
776 | |
777 | // --------------------------------------------------------------------------------------- |
778 | // Pow |
779 | |
780 | /// 0^0 = 1 |
781 | impl Pow<Z0> for Z0 { |
782 | type Output = P1; |
783 | #[inline ] |
784 | fn powi(self, _: Z0) -> Self::Output { |
785 | P1::new() |
786 | } |
787 | } |
788 | |
789 | /// 0^P = 0 |
790 | impl<U: Unsigned + NonZero> Pow<PInt<U>> for Z0 { |
791 | type Output = Z0; |
792 | #[inline ] |
793 | fn powi(self, _: PInt<U>) -> Self::Output { |
794 | Z0 |
795 | } |
796 | } |
797 | |
798 | /// 0^N = 0 |
799 | impl<U: Unsigned + NonZero> Pow<NInt<U>> for Z0 { |
800 | type Output = Z0; |
801 | #[inline ] |
802 | fn powi(self, _: NInt<U>) -> Self::Output { |
803 | Z0 |
804 | } |
805 | } |
806 | |
807 | /// 1^N = 1 |
808 | impl<U: Unsigned + NonZero> Pow<NInt<U>> for P1 { |
809 | type Output = P1; |
810 | #[inline ] |
811 | fn powi(self, _: NInt<U>) -> Self::Output { |
812 | P1::new() |
813 | } |
814 | } |
815 | |
816 | /// (-1)^N = 1 if N is even |
817 | impl<U: Unsigned> Pow<NInt<UInt<U, B0>>> for N1 { |
818 | type Output = P1; |
819 | #[inline ] |
820 | fn powi(self, _: NInt<UInt<U, B0>>) -> Self::Output { |
821 | P1::new() |
822 | } |
823 | } |
824 | |
825 | /// (-1)^N = -1 if N is odd |
826 | impl<U: Unsigned> Pow<NInt<UInt<U, B1>>> for N1 { |
827 | type Output = N1; |
828 | #[inline ] |
829 | fn powi(self, _: NInt<UInt<U, B1>>) -> Self::Output { |
830 | N1::new() |
831 | } |
832 | } |
833 | |
834 | /// P^0 = 1 |
835 | impl<U: Unsigned + NonZero> Pow<Z0> for PInt<U> { |
836 | type Output = P1; |
837 | #[inline ] |
838 | fn powi(self, _: Z0) -> Self::Output { |
839 | P1::new() |
840 | } |
841 | } |
842 | |
843 | /// N^0 = 1 |
844 | impl<U: Unsigned + NonZero> Pow<Z0> for NInt<U> { |
845 | type Output = P1; |
846 | #[inline ] |
847 | fn powi(self, _: Z0) -> Self::Output { |
848 | P1::new() |
849 | } |
850 | } |
851 | |
852 | /// P(Ul)^P(Ur) = P(Ul^Ur) |
853 | impl<Ul: Unsigned + NonZero, Ur: Unsigned + NonZero> Pow<PInt<Ur>> for PInt<Ul> |
854 | where |
855 | Ul: Pow<Ur>, |
856 | <Ul as Pow<Ur>>::Output: Unsigned + NonZero, |
857 | { |
858 | type Output = PInt<<Ul as Pow<Ur>>::Output>; |
859 | #[inline ] |
860 | fn powi(self, _: PInt<Ur>) -> Self::Output { |
861 | PInt::new() |
862 | } |
863 | } |
864 | |
865 | /// N(Ul)^P(Ur) = P(Ul^Ur) if Ur is even |
866 | impl<Ul: Unsigned + NonZero, Ur: Unsigned> Pow<PInt<UInt<Ur, B0>>> for NInt<Ul> |
867 | where |
868 | Ul: Pow<UInt<Ur, B0>>, |
869 | <Ul as Pow<UInt<Ur, B0>>>::Output: Unsigned + NonZero, |
870 | { |
871 | type Output = PInt<<Ul as Pow<UInt<Ur, B0>>>::Output>; |
872 | #[inline ] |
873 | fn powi(self, _: PInt<UInt<Ur, B0>>) -> Self::Output { |
874 | PInt::new() |
875 | } |
876 | } |
877 | |
878 | /// N(Ul)^P(Ur) = N(Ul^Ur) if Ur is odd |
879 | impl<Ul: Unsigned + NonZero, Ur: Unsigned> Pow<PInt<UInt<Ur, B1>>> for NInt<Ul> |
880 | where |
881 | Ul: Pow<UInt<Ur, B1>>, |
882 | <Ul as Pow<UInt<Ur, B1>>>::Output: Unsigned + NonZero, |
883 | { |
884 | type Output = NInt<<Ul as Pow<UInt<Ur, B1>>>::Output>; |
885 | #[inline ] |
886 | fn powi(self, _: PInt<UInt<Ur, B1>>) -> Self::Output { |
887 | NInt::new() |
888 | } |
889 | } |
890 | |
891 | // --------------------------------------------------------------------------------------- |
892 | // Gcd |
893 | use crate::{Gcd, Gcf}; |
894 | |
895 | impl Gcd<Z0> for Z0 { |
896 | type Output = Z0; |
897 | } |
898 | |
899 | impl<U> Gcd<PInt<U>> for Z0 |
900 | where |
901 | U: Unsigned + NonZero, |
902 | { |
903 | type Output = PInt<U>; |
904 | } |
905 | |
906 | impl<U> Gcd<Z0> for PInt<U> |
907 | where |
908 | U: Unsigned + NonZero, |
909 | { |
910 | type Output = PInt<U>; |
911 | } |
912 | |
913 | impl<U> Gcd<NInt<U>> for Z0 |
914 | where |
915 | U: Unsigned + NonZero, |
916 | { |
917 | type Output = PInt<U>; |
918 | } |
919 | |
920 | impl<U> Gcd<Z0> for NInt<U> |
921 | where |
922 | U: Unsigned + NonZero, |
923 | { |
924 | type Output = PInt<U>; |
925 | } |
926 | |
927 | impl<U1, U2> Gcd<PInt<U2>> for PInt<U1> |
928 | where |
929 | U1: Unsigned + NonZero + Gcd<U2>, |
930 | U2: Unsigned + NonZero, |
931 | Gcf<U1, U2>: Unsigned + NonZero, |
932 | { |
933 | type Output = PInt<Gcf<U1, U2>>; |
934 | } |
935 | |
936 | impl<U1, U2> Gcd<PInt<U2>> for NInt<U1> |
937 | where |
938 | U1: Unsigned + NonZero + Gcd<U2>, |
939 | U2: Unsigned + NonZero, |
940 | Gcf<U1, U2>: Unsigned + NonZero, |
941 | { |
942 | type Output = PInt<Gcf<U1, U2>>; |
943 | } |
944 | |
945 | impl<U1, U2> Gcd<NInt<U2>> for PInt<U1> |
946 | where |
947 | U1: Unsigned + NonZero + Gcd<U2>, |
948 | U2: Unsigned + NonZero, |
949 | Gcf<U1, U2>: Unsigned + NonZero, |
950 | { |
951 | type Output = PInt<Gcf<U1, U2>>; |
952 | } |
953 | |
954 | impl<U1, U2> Gcd<NInt<U2>> for NInt<U1> |
955 | where |
956 | U1: Unsigned + NonZero + Gcd<U2>, |
957 | U2: Unsigned + NonZero, |
958 | Gcf<U1, U2>: Unsigned + NonZero, |
959 | { |
960 | type Output = PInt<Gcf<U1, U2>>; |
961 | } |
962 | |
963 | // --------------------------------------------------------------------------------------- |
964 | // Min |
965 | use crate::{Max, Maximum, Min, Minimum}; |
966 | |
967 | impl Min<Z0> for Z0 { |
968 | type Output = Z0; |
969 | #[inline ] |
970 | fn min(self, _: Z0) -> Self::Output { |
971 | self |
972 | } |
973 | } |
974 | |
975 | impl<U> Min<PInt<U>> for Z0 |
976 | where |
977 | U: Unsigned + NonZero, |
978 | { |
979 | type Output = Z0; |
980 | #[inline ] |
981 | fn min(self, _: PInt<U>) -> Self::Output { |
982 | self |
983 | } |
984 | } |
985 | |
986 | impl<U> Min<NInt<U>> for Z0 |
987 | where |
988 | U: Unsigned + NonZero, |
989 | { |
990 | type Output = NInt<U>; |
991 | #[inline ] |
992 | fn min(self, rhs: NInt<U>) -> Self::Output { |
993 | rhs |
994 | } |
995 | } |
996 | |
997 | impl<U> Min<Z0> for PInt<U> |
998 | where |
999 | U: Unsigned + NonZero, |
1000 | { |
1001 | type Output = Z0; |
1002 | #[inline ] |
1003 | fn min(self, rhs: Z0) -> Self::Output { |
1004 | rhs |
1005 | } |
1006 | } |
1007 | |
1008 | impl<U> Min<Z0> for NInt<U> |
1009 | where |
1010 | U: Unsigned + NonZero, |
1011 | { |
1012 | type Output = NInt<U>; |
1013 | #[inline ] |
1014 | fn min(self, _: Z0) -> Self::Output { |
1015 | self |
1016 | } |
1017 | } |
1018 | |
1019 | impl<Ul, Ur> Min<PInt<Ur>> for PInt<Ul> |
1020 | where |
1021 | Ul: Unsigned + NonZero + Min<Ur>, |
1022 | Ur: Unsigned + NonZero, |
1023 | Minimum<Ul, Ur>: Unsigned + NonZero, |
1024 | { |
1025 | type Output = PInt<Minimum<Ul, Ur>>; |
1026 | #[inline ] |
1027 | fn min(self, rhs: PInt<Ur>) -> Self::Output { |
1028 | PInt { |
1029 | n: self.n.min(rhs.n), |
1030 | } |
1031 | } |
1032 | } |
1033 | |
1034 | impl<Ul, Ur> Min<PInt<Ur>> for NInt<Ul> |
1035 | where |
1036 | Ul: Unsigned + NonZero, |
1037 | Ur: Unsigned + NonZero, |
1038 | { |
1039 | type Output = NInt<Ul>; |
1040 | #[inline ] |
1041 | fn min(self, _: PInt<Ur>) -> Self::Output { |
1042 | self |
1043 | } |
1044 | } |
1045 | |
1046 | impl<Ul, Ur> Min<NInt<Ur>> for PInt<Ul> |
1047 | where |
1048 | Ul: Unsigned + NonZero, |
1049 | Ur: Unsigned + NonZero, |
1050 | { |
1051 | type Output = NInt<Ur>; |
1052 | #[inline ] |
1053 | fn min(self, rhs: NInt<Ur>) -> Self::Output { |
1054 | rhs |
1055 | } |
1056 | } |
1057 | |
1058 | impl<Ul, Ur> Min<NInt<Ur>> for NInt<Ul> |
1059 | where |
1060 | Ul: Unsigned + NonZero + Max<Ur>, |
1061 | Ur: Unsigned + NonZero, |
1062 | Maximum<Ul, Ur>: Unsigned + NonZero, |
1063 | { |
1064 | type Output = NInt<Maximum<Ul, Ur>>; |
1065 | #[inline ] |
1066 | fn min(self, rhs: NInt<Ur>) -> Self::Output { |
1067 | NInt { |
1068 | n: self.n.max(rhs.n), |
1069 | } |
1070 | } |
1071 | } |
1072 | |
1073 | // --------------------------------------------------------------------------------------- |
1074 | // Max |
1075 | |
1076 | impl Max<Z0> for Z0 { |
1077 | type Output = Z0; |
1078 | #[inline ] |
1079 | fn max(self, _: Z0) -> Self::Output { |
1080 | self |
1081 | } |
1082 | } |
1083 | |
1084 | impl<U> Max<PInt<U>> for Z0 |
1085 | where |
1086 | U: Unsigned + NonZero, |
1087 | { |
1088 | type Output = PInt<U>; |
1089 | #[inline ] |
1090 | fn max(self, rhs: PInt<U>) -> Self::Output { |
1091 | rhs |
1092 | } |
1093 | } |
1094 | |
1095 | impl<U> Max<NInt<U>> for Z0 |
1096 | where |
1097 | U: Unsigned + NonZero, |
1098 | { |
1099 | type Output = Z0; |
1100 | #[inline ] |
1101 | fn max(self, _: NInt<U>) -> Self::Output { |
1102 | self |
1103 | } |
1104 | } |
1105 | |
1106 | impl<U> Max<Z0> for PInt<U> |
1107 | where |
1108 | U: Unsigned + NonZero, |
1109 | { |
1110 | type Output = PInt<U>; |
1111 | #[inline ] |
1112 | fn max(self, _: Z0) -> Self::Output { |
1113 | self |
1114 | } |
1115 | } |
1116 | |
1117 | impl<U> Max<Z0> for NInt<U> |
1118 | where |
1119 | U: Unsigned + NonZero, |
1120 | { |
1121 | type Output = Z0; |
1122 | #[inline ] |
1123 | fn max(self, rhs: Z0) -> Self::Output { |
1124 | rhs |
1125 | } |
1126 | } |
1127 | |
1128 | impl<Ul, Ur> Max<PInt<Ur>> for PInt<Ul> |
1129 | where |
1130 | Ul: Unsigned + NonZero + Max<Ur>, |
1131 | Ur: Unsigned + NonZero, |
1132 | Maximum<Ul, Ur>: Unsigned + NonZero, |
1133 | { |
1134 | type Output = PInt<Maximum<Ul, Ur>>; |
1135 | #[inline ] |
1136 | fn max(self, rhs: PInt<Ur>) -> Self::Output { |
1137 | PInt { |
1138 | n: self.n.max(rhs.n), |
1139 | } |
1140 | } |
1141 | } |
1142 | |
1143 | impl<Ul, Ur> Max<PInt<Ur>> for NInt<Ul> |
1144 | where |
1145 | Ul: Unsigned + NonZero, |
1146 | Ur: Unsigned + NonZero, |
1147 | { |
1148 | type Output = PInt<Ur>; |
1149 | #[inline ] |
1150 | fn max(self, rhs: PInt<Ur>) -> Self::Output { |
1151 | rhs |
1152 | } |
1153 | } |
1154 | |
1155 | impl<Ul, Ur> Max<NInt<Ur>> for PInt<Ul> |
1156 | where |
1157 | Ul: Unsigned + NonZero, |
1158 | Ur: Unsigned + NonZero, |
1159 | { |
1160 | type Output = PInt<Ul>; |
1161 | #[inline ] |
1162 | fn max(self, _: NInt<Ur>) -> Self::Output { |
1163 | self |
1164 | } |
1165 | } |
1166 | |
1167 | impl<Ul, Ur> Max<NInt<Ur>> for NInt<Ul> |
1168 | where |
1169 | Ul: Unsigned + NonZero + Min<Ur>, |
1170 | Ur: Unsigned + NonZero, |
1171 | Minimum<Ul, Ur>: Unsigned + NonZero, |
1172 | { |
1173 | type Output = NInt<Minimum<Ul, Ur>>; |
1174 | #[inline ] |
1175 | fn max(self, rhs: NInt<Ur>) -> Self::Output { |
1176 | NInt { |
1177 | n: self.n.min(rhs.n), |
1178 | } |
1179 | } |
1180 | } |
1181 | |
1182 | // ----------------------------------------- |
1183 | // ToInt |
1184 | |
1185 | impl ToInt<i8> for Z0 { |
1186 | #[inline ] |
1187 | fn to_int() -> i8 { |
1188 | Self::I8 |
1189 | } |
1190 | const INT: i8 = Self::I8; |
1191 | } |
1192 | |
1193 | impl ToInt<i16> for Z0 { |
1194 | #[inline ] |
1195 | fn to_int() -> i16 { |
1196 | Self::I16 |
1197 | } |
1198 | const INT: i16 = Self::I16; |
1199 | } |
1200 | |
1201 | impl ToInt<i32> for Z0 { |
1202 | #[inline ] |
1203 | fn to_int() -> i32 { |
1204 | Self::I32 |
1205 | } |
1206 | const INT: i32 = Self::I32; |
1207 | } |
1208 | |
1209 | impl ToInt<i64> for Z0 { |
1210 | #[inline ] |
1211 | fn to_int() -> i64 { |
1212 | Self::I64 |
1213 | } |
1214 | const INT: i64 = Self::I64; |
1215 | } |
1216 | |
1217 | // negative numbers |
1218 | |
1219 | impl<U> ToInt<i8> for NInt<U> |
1220 | where |
1221 | U: Unsigned + NonZero, |
1222 | { |
1223 | #[inline ] |
1224 | fn to_int() -> i8 { |
1225 | Self::I8 |
1226 | } |
1227 | const INT: i8 = Self::I8; |
1228 | } |
1229 | |
1230 | impl<U> ToInt<i16> for NInt<U> |
1231 | where |
1232 | U: Unsigned + NonZero, |
1233 | { |
1234 | #[inline ] |
1235 | fn to_int() -> i16 { |
1236 | Self::I16 |
1237 | } |
1238 | const INT: i16 = Self::I16; |
1239 | } |
1240 | |
1241 | impl<U> ToInt<i32> for NInt<U> |
1242 | where |
1243 | U: Unsigned + NonZero, |
1244 | { |
1245 | #[inline ] |
1246 | fn to_int() -> i32 { |
1247 | Self::I32 |
1248 | } |
1249 | const INT: i32 = Self::I32; |
1250 | } |
1251 | |
1252 | impl<U> ToInt<i64> for NInt<U> |
1253 | where |
1254 | U: Unsigned + NonZero, |
1255 | { |
1256 | #[inline ] |
1257 | fn to_int() -> i64 { |
1258 | Self::I64 |
1259 | } |
1260 | const INT: i64 = Self::I64; |
1261 | } |
1262 | |
1263 | // positive numbers |
1264 | |
1265 | impl<U> ToInt<i8> for PInt<U> |
1266 | where |
1267 | U: Unsigned + NonZero, |
1268 | { |
1269 | #[inline ] |
1270 | fn to_int() -> i8 { |
1271 | Self::I8 |
1272 | } |
1273 | const INT: i8 = Self::I8; |
1274 | } |
1275 | |
1276 | impl<U> ToInt<i16> for PInt<U> |
1277 | where |
1278 | U: Unsigned + NonZero, |
1279 | { |
1280 | #[inline ] |
1281 | fn to_int() -> i16 { |
1282 | Self::I16 |
1283 | } |
1284 | const INT: i16 = Self::I16; |
1285 | } |
1286 | |
1287 | impl<U> ToInt<i32> for PInt<U> |
1288 | where |
1289 | U: Unsigned + NonZero, |
1290 | { |
1291 | #[inline ] |
1292 | fn to_int() -> i32 { |
1293 | Self::I32 |
1294 | } |
1295 | const INT: i32 = Self::I32; |
1296 | } |
1297 | |
1298 | impl<U> ToInt<i64> for PInt<U> |
1299 | where |
1300 | U: Unsigned + NonZero, |
1301 | { |
1302 | #[inline ] |
1303 | fn to_int() -> i64 { |
1304 | Self::I64 |
1305 | } |
1306 | const INT: i64 = Self::I64; |
1307 | } |
1308 | |
1309 | #[cfg (test)] |
1310 | mod tests { |
1311 | use crate::{consts::*, Integer, ToInt}; |
1312 | |
1313 | #[test ] |
1314 | fn to_ix_min() { |
1315 | assert_eq!(N128::to_i8(), ::core::i8::MIN); |
1316 | assert_eq!(N32768::to_i16(), ::core::i16::MIN); |
1317 | } |
1318 | |
1319 | #[test ] |
1320 | fn int_toint_test() { |
1321 | // i8 |
1322 | assert_eq!(0_i8, Z0::to_int()); |
1323 | assert_eq!(1_i8, P1::to_int()); |
1324 | assert_eq!(2_i8, P2::to_int()); |
1325 | assert_eq!(3_i8, P3::to_int()); |
1326 | assert_eq!(4_i8, P4::to_int()); |
1327 | assert_eq!(-1_i8, N1::to_int()); |
1328 | assert_eq!(-2_i8, N2::to_int()); |
1329 | assert_eq!(-3_i8, N3::to_int()); |
1330 | assert_eq!(-4_i8, N4::to_int()); |
1331 | assert_eq!(0_i8, Z0::INT); |
1332 | assert_eq!(1_i8, P1::INT); |
1333 | assert_eq!(2_i8, P2::INT); |
1334 | assert_eq!(3_i8, P3::INT); |
1335 | assert_eq!(4_i8, P4::INT); |
1336 | assert_eq!(-1_i8, N1::INT); |
1337 | assert_eq!(-2_i8, N2::INT); |
1338 | assert_eq!(-3_i8, N3::INT); |
1339 | assert_eq!(-4_i8, N4::INT); |
1340 | |
1341 | // i16 |
1342 | assert_eq!(0_i16, Z0::to_int()); |
1343 | assert_eq!(1_i16, P1::to_int()); |
1344 | assert_eq!(2_i16, P2::to_int()); |
1345 | assert_eq!(3_i16, P3::to_int()); |
1346 | assert_eq!(4_i16, P4::to_int()); |
1347 | assert_eq!(-1_i16, N1::to_int()); |
1348 | assert_eq!(-2_i16, N2::to_int()); |
1349 | assert_eq!(-3_i16, N3::to_int()); |
1350 | assert_eq!(-4_i16, N4::to_int()); |
1351 | assert_eq!(0_i16, Z0::INT); |
1352 | assert_eq!(1_i16, P1::INT); |
1353 | assert_eq!(2_i16, P2::INT); |
1354 | assert_eq!(3_i16, P3::INT); |
1355 | assert_eq!(4_i16, P4::INT); |
1356 | assert_eq!(-1_i16, N1::INT); |
1357 | assert_eq!(-2_i16, N2::INT); |
1358 | assert_eq!(-3_i16, N3::INT); |
1359 | assert_eq!(-4_i16, N4::INT); |
1360 | |
1361 | // i32 |
1362 | assert_eq!(0_i32, Z0::to_int()); |
1363 | assert_eq!(1_i32, P1::to_int()); |
1364 | assert_eq!(2_i32, P2::to_int()); |
1365 | assert_eq!(3_i32, P3::to_int()); |
1366 | assert_eq!(4_i32, P4::to_int()); |
1367 | assert_eq!(-1_i32, N1::to_int()); |
1368 | assert_eq!(-2_i32, N2::to_int()); |
1369 | assert_eq!(-3_i32, N3::to_int()); |
1370 | assert_eq!(-4_i32, N4::to_int()); |
1371 | assert_eq!(0_i32, Z0::INT); |
1372 | assert_eq!(1_i32, P1::INT); |
1373 | assert_eq!(2_i32, P2::INT); |
1374 | assert_eq!(3_i32, P3::INT); |
1375 | assert_eq!(4_i32, P4::INT); |
1376 | assert_eq!(-1_i32, N1::INT); |
1377 | assert_eq!(-2_i32, N2::INT); |
1378 | assert_eq!(-3_i32, N3::INT); |
1379 | assert_eq!(-4_i32, N4::INT); |
1380 | |
1381 | // i64 |
1382 | assert_eq!(0_i64, Z0::to_int()); |
1383 | assert_eq!(1_i64, P1::to_int()); |
1384 | assert_eq!(2_i64, P2::to_int()); |
1385 | assert_eq!(3_i64, P3::to_int()); |
1386 | assert_eq!(4_i64, P4::to_int()); |
1387 | assert_eq!(-1_i64, N1::to_int()); |
1388 | assert_eq!(-2_i64, N2::to_int()); |
1389 | assert_eq!(-3_i64, N3::to_int()); |
1390 | assert_eq!(-4_i64, N4::to_int()); |
1391 | assert_eq!(0_i64, Z0::INT); |
1392 | assert_eq!(1_i64, P1::INT); |
1393 | assert_eq!(2_i64, P2::INT); |
1394 | assert_eq!(3_i64, P3::INT); |
1395 | assert_eq!(4_i64, P4::INT); |
1396 | assert_eq!(-1_i64, N1::INT); |
1397 | assert_eq!(-2_i64, N2::INT); |
1398 | assert_eq!(-3_i64, N3::INT); |
1399 | assert_eq!(-4_i64, N4::INT); |
1400 | } |
1401 | } |
1402 | |