1#![warn(missing_docs)]
3
4mod float;
5mod real;
6
7pub use float::*;
8pub use real::*;
9
10pub trait UNum:
12 Sized
13 + Copy
14 + std::fmt::Debug
15 + std::fmt::Display
16 + std::ops::Add<Output = Self>
17 + std::ops::AddAssign
18 + std::ops::Sub<Output = Self>
19 + std::ops::SubAssign
20 + std::ops::Mul<Output = Self>
21 + std::ops::MulAssign
22 + std::ops::Div<Output = Self>
23 + std::ops::DivAssign
24 + PartialEq
25 + PartialOrd
26 + ::rand::distributions::uniform::SampleUniform
27{
28 const ZERO: Self;
30
31 const ONE: Self;
33
34 fn sqr(self) -> Self {
36 self * self
37 }
38}
39
40pub trait Num: UNum + std::ops::Neg<Output = Self> {
42 fn signum(self) -> Self;
44
45 fn abs(self) -> Self {
47 if self >= Self::ZERO {
48 self
49 } else {
50 -self
51 }
52 }
53}
54
55macro_rules! impl_int {
56 ($($t:ty),*) => {
57 $(
58 impl UNum for $t {
59 const ZERO: Self = 0;
60 const ONE: Self = 1;
61 }
62 )*
63 };
64}
65
66macro_rules! impl_signed_int {
67 ($($t:ty),*) => {
68 $(
69 impl_int!($t);
70
71 impl Num for $t {
72 fn signum(self) -> Self {
73 match self {
74 _ if self > 0 => 1,
75 0 => 0,
76 _ => -1,
77 }
78 }
79 }
80 )*
81 }
82}
83
84impl_int! { u8, u16, u32, u64, usize }
85impl_signed_int! { i8, i16, i32, i64, isize }