1use crate::PrimitiveError;
2
3trait Sealed {}
4
5#[expect(private_bounds)]
45pub trait PrimitiveNumber:
46 'static
47 + Sealed
48 + core::cmp::PartialEq
49 + core::cmp::PartialOrd
50 + core::convert::From<bool>
51 + core::default::Default
52 + core::fmt::Debug
53 + core::fmt::Display
54 + core::fmt::LowerExp
55 + core::fmt::UpperExp
56 + core::iter::Product<Self>
57 + core::iter::Sum<Self>
58 + core::marker::Copy
59 + core::marker::Send
60 + core::marker::Sync
61 + core::marker::Unpin
62 + core::ops::Add<Self, Output = Self>
63 + core::ops::AddAssign<Self>
64 + core::ops::Div<Self, Output = Self>
65 + core::ops::DivAssign<Self>
66 + core::ops::Mul<Self, Output = Self>
67 + core::ops::MulAssign<Self>
68 + core::ops::Rem<Self, Output = Self>
69 + core::ops::RemAssign<Self>
70 + core::ops::Sub<Self, Output = Self>
71 + core::ops::SubAssign<Self>
72 + core::panic::RefUnwindSafe
73 + core::panic::UnwindSafe
74 + core::str::FromStr<Err: PrimitiveError>
75 + for<'a> core::iter::Product<&'a Self>
76 + for<'a> core::iter::Sum<&'a Self>
77 + for<'a> core::ops::Add<&'a Self, Output = Self>
78 + for<'a> core::ops::AddAssign<&'a Self>
79 + for<'a> core::ops::Div<&'a Self, Output = Self>
80 + for<'a> core::ops::DivAssign<&'a Self>
81 + for<'a> core::ops::Mul<&'a Self, Output = Self>
82 + for<'a> core::ops::MulAssign<&'a Self>
83 + for<'a> core::ops::Rem<&'a Self, Output = Self>
84 + for<'a> core::ops::RemAssign<&'a Self>
85 + for<'a> core::ops::Sub<&'a Self, Output = Self>
86 + for<'a> core::ops::SubAssign<&'a Self>
87{
88 type Bytes: core::borrow::Borrow<[u8]> + core::borrow::BorrowMut<[u8]>;
91
92 fn from_be_bytes(bytes: Self::Bytes) -> Self;
94
95 fn from_le_bytes(bytes: Self::Bytes) -> Self;
97
98 fn from_ne_bytes(bytes: Self::Bytes) -> Self;
100
101 fn to_be_bytes(self) -> Self::Bytes;
103
104 fn to_le_bytes(self) -> Self::Bytes;
106
107 fn to_ne_bytes(self) -> Self::Bytes;
109}
110
111#[expect(private_bounds)]
116pub trait PrimitiveNumberRef<T>:
117 Sealed
118 + core::borrow::Borrow<T>
119 + core::cmp::PartialEq
120 + core::cmp::PartialOrd
121 + core::fmt::Debug
122 + core::fmt::Display
123 + core::fmt::LowerExp
124 + core::fmt::UpperExp
125 + core::marker::Copy
126 + core::marker::Send
127 + core::marker::Sync
128 + core::marker::Unpin
129 + core::ops::Add<T, Output = T>
130 + core::ops::Deref<Target = T>
131 + core::ops::Div<T, Output = T>
132 + core::ops::Mul<T, Output = T>
133 + core::ops::Rem<T, Output = T>
134 + core::ops::Sub<T, Output = T>
135 + core::panic::RefUnwindSafe
136 + core::panic::UnwindSafe
137 + for<'a> core::ops::Add<&'a T, Output = T>
138 + for<'a> core::ops::Div<&'a T, Output = T>
139 + for<'a> core::ops::Mul<&'a T, Output = T>
140 + for<'a> core::ops::Rem<&'a T, Output = T>
141 + for<'a> core::ops::Sub<&'a T, Output = T>
142{
143}
144
145macro_rules! impl_primitive {
146 ($($Number:ident),*) => {$(
147 impl Sealed for $Number {}
148 impl Sealed for &$Number {}
149
150 impl PrimitiveNumber for $Number {
151 type Bytes = [u8; size_of::<Self>()];
152
153 forward! {
154 fn from_be_bytes(bytes: Self::Bytes) -> Self;
155 fn from_le_bytes(bytes: Self::Bytes) -> Self;
156 fn from_ne_bytes(bytes: Self::Bytes) -> Self;
157 }
158 forward! {
159 fn to_be_bytes(self) -> Self::Bytes;
160 fn to_le_bytes(self) -> Self::Bytes;
161 fn to_ne_bytes(self) -> Self::Bytes;
162 }
163 }
164
165 impl PrimitiveNumberRef<$Number> for &$Number {}
166 )*}
167}
168
169impl_primitive!(f32, f64);
170impl_primitive!(i8, i16, i32, i64, i128, isize);
171impl_primitive!(u8, u16, u32, u64, u128, usize);