1use super::*;
2
3
4pub trait Zero : Sized
6{
7 const ZERO : Self;
9 #[inline(always)] fn zero() -> Self { Self::ZERO }
10
11 #[inline(always)] fn set_zero(&mut self) -> &mut Self { *self = Self::ZERO; self }
12
13 #[inline(always)] fn is_zero(&self) -> bool where Self : PartialEq<Self> { self == &Self::ZERO }
14 #[inline(always)] fn is_non_zero(&self) -> bool where Self : PartialEq<Self> { !self.is_zero() }
15}
16pub const fn zero<T : Zero>() -> T { T::ZERO }
17map_on_number!(($primitive_name: ty) => { impl Zero for $primitive_name { const ZERO : Self = 0 as Self; } });
18
19impl<T> Zero for Wrapping<T> where T: Zero { const ZERO : Self = Wrapping(T::ZERO); }
20impl<T> Zero for Saturating<T> where T: Zero { const ZERO : Self = Saturating(T::ZERO); }
21
22impl<T, const N : usize> Zero for [T;N] where T: Zero
23{
24 const ZERO : Self = [T::ZERO; N];
25}
26impl Zero for bool { const ZERO : Self = false; }
27
28
29pub trait ZeroIter
30{
31 fn all_zero(&self) -> bool;
32 fn all_non_zero(&self) -> bool;
33
34 fn any_zero(&self) -> bool;
35 fn any_non_zero(&self) -> bool;
36}
37impl<T,Z> ZeroIter for T where for<'a> &'a T: IntoIterator<Item = &'a Z>, Z: Zero + PartialEq
38{
39 fn all_zero(&self) -> bool { self.into_iter().all(|v| v.is_zero()) }
40 fn all_non_zero(&self) -> bool { self.into_iter().all(|v| v.is_non_zero()) }
41
42 fn any_zero(&self) -> bool { self.into_iter().any(|v| v.is_zero()) }
43 fn any_non_zero(&self) -> bool { self.into_iter().any(|v| v.is_non_zero()) }
44}
45
46
47pub trait UnwrapZero
48{
49 type Output : Zero;
50 fn unwrap_or_zero(self) -> Self::Output;
51}
52impl<T> UnwrapZero for Option<T> where T: Zero { type Output = T; fn unwrap_or_zero(self) -> Self::Output { self.unwrap_or(T::ZERO) }}
53impl<T,E> UnwrapZero for Result<T,E> where T: Zero { type Output = T; fn unwrap_or_zero(self) -> Self::Output { self.unwrap_or(T::ZERO) }}
54
55
56
57
58pub trait One : Sized
60{
61 const ONE : Self;
63 #[inline(always)] fn one() -> Self where Self : Sized { Self::ONE }
64
65 #[inline(always)] fn set_one(&mut self) -> &mut Self { *self = Self::ONE; self }
66
67 #[inline(always)] fn is_one(&self) -> bool where Self : PartialEq<Self> { self == &Self::ONE }
68 #[inline(always)] fn is_non_one(&self) -> bool where Self : PartialEq<Self> { !self.is_one() }
69}
70pub const fn one<T : One>() -> T { T::ONE }
71
72map_on_number!(($primitive_name: ty) => { impl One for $primitive_name { const ONE : Self = 1 as Self; } });
73
74impl<T> One for Wrapping<T> where T: One { const ONE : Self = Wrapping(T::ONE); }
75impl<T> One for Saturating<T> where T: One { const ONE : Self = Saturating(T::ONE); }
76
77impl<T, const N : usize> One for [T;N] where T: One
78{
79 const ONE : Self = [T::ONE; N];
80}
81impl One for bool { const ONE : Self = true; }
82
83
84
85pub trait OneIter
86{
87 fn all_one(&self) -> bool;
88 fn any_one(&self) -> bool;
89}
90impl<T,Z> OneIter for T where for<'a> &'a T: IntoIterator<Item = &'a Z>, Z: One + PartialEq
91{
92 fn all_one(&self) -> bool
93 {
94 self.into_iter().all(|v| v.is_one())
95 }
96 fn any_one(&self) -> bool {
97 self.into_iter().any(|v| v.is_one())
98 }
99}
100
101
102pub trait MinusOne : Sized
104{
105 const MINUS_ONE : Self;
106
107 #[inline(always)] fn minus_one() -> Self where Self : Sized { Self::MINUS_ONE }
108 #[inline(always)] fn set_minus_one(&mut self) -> &mut Self { *self = Self::MINUS_ONE; self }
109
110 #[inline(always)] fn is_minus_one(&self) -> bool where Self : PartialEq<Self> { self == &Self::MINUS_ONE }
111 #[inline(always)] fn is_non_minus_one(&self) -> bool where Self : PartialEq<Self> { !self.is_minus_one() }
112}
113pub const fn minus_one<T : MinusOne>() -> T { T::MINUS_ONE }
114
115map_on_number!(($primitive_name: ty) => { impl MinusOne for $primitive_name { const MINUS_ONE : Self = 1 as Self; } });
116impl<T> MinusOne for Wrapping<T> where T: MinusOne { const MINUS_ONE : Self = Wrapping(T::MINUS_ONE); }
117impl<T> MinusOne for Saturating<T> where T: MinusOne { const MINUS_ONE : Self = Saturating(T::MINUS_ONE); }
118
119impl<T, const N : usize> MinusOne for [T;N] where T: MinusOne
120{
121 const MINUS_ONE : Self = [T::MINUS_ONE; N];
122}
123
124pub trait MinusOneIter
125{
126 fn all_minusone(&self) -> bool;
127 fn any_minusone(&self) -> bool;
128}
129impl<T,Z> MinusOneIter for T where for<'a> &'a T: IntoIterator<Item = &'a Z>, Z: MinusOne + PartialEq
130{
131 fn all_minusone(&self) -> bool
132 {
133 self.into_iter().all(|v| v.is_minus_one())
134 }
135 fn any_minusone(&self) -> bool {
136 self.into_iter().any(|v| v.is_minus_one())
137 }
138}
139
140
141
142
143
144pub trait Half : Sized
146{
147 const HALF : Self;
148
149 #[inline(always)] fn half() -> Self where Self : Sized { Self::HALF }
150 #[inline(always)] fn set_half(&mut self) -> &mut Self { *self = Self::HALF; self }
151
152 #[inline(always)] fn is_half(self) -> bool where Self : PartialEq<Self> { self == Self::HALF }
153 #[inline(always)] fn is_non_half(self) -> bool where Self : PartialEq<Self> { !self.is_half() }
154}
155pub const fn half<T : Half>() -> T { T::HALF }
156
157map_on_float!(($primitive_name: ty) => { impl Half for $primitive_name { const HALF : Self = 0.5; } });
158impl<T> Half for Wrapping<T> where T: Half { const HALF : Self = Wrapping(T::HALF); }
159impl<T> Half for Saturating<T> where T: Half { const HALF : Self = Saturating(T::HALF); }
160
161impl<T, const N : usize> Half for [T;N] where T: Half
162{
163 const HALF : Self = [T::HALF; N];
164}
165
166
167
168pub trait NaNValue : Sized
170{
171 const NAN : Self;
172 #[inline(always)] fn is_nan(&self) -> bool where Self : PartialEq { self == &Self::NAN }
173 #[inline(always)] fn is_not_nan(&self) -> bool where Self : PartialEq { !self.is_nan() }
174}
175map_on_float!(($primitive_name: ty) => { impl NaNValue for $primitive_name { const NAN : Self = Self::NAN; }};);
176
177impl<T, const N : usize> NaNValue for [T;N] where T: NaNValue
178{
179 const NAN : Self = [T::NAN; N];
180}
181
182
183
184pub trait MinValue : Sized
185{
186 const MIN : Self;
187 #[inline(always)] fn is_min_value(&self) -> bool where Self : PartialEq { self == &Self::MIN }
188 #[inline(always)] fn is_not_min_value(&self) -> bool where Self : PartialEq { !self.is_min_value() }
189}
190
191
192map_on_number!(($primitive_name: ty) => { impl MinValue for $primitive_name { const MIN : Self = Self::MIN; }});
193impl MinValue for bool { const MIN : Self = false; }
194impl<T> MinValue for Wrapping<T> where T: MinValue { const MIN : Self = Wrapping(T::MIN); }
195impl<T> MinValue for Saturating<T> where T: MinValue { const MIN : Self = Saturating(T::MIN); }
196
197impl<T, const N : usize> MinValue for [T;N] where T: MinValue
198{
199 const MIN : Self = [T::MIN; N];
200}
201
202pub trait MaxValue : Sized
203{
204 const MAX : Self;
205 #[inline(always)] fn is_max_value(&self) -> bool where Self : PartialEq { self == &Self::MAX }
206 #[inline(always)] fn is_non_max_value(&self) -> bool where Self : PartialEq { !self.is_max_value() }
207}
208map_on_number!(($primitive_name: ty) => { impl MaxValue for $primitive_name { const MAX : Self = Self::MAX; } });
209impl MaxValue for bool { const MAX : Self = true; }
210impl<T> MaxValue for Wrapping<T> where T: MaxValue { const MAX : Self = Wrapping(T::MAX); }
211impl<T> MaxValue for Saturating<T> where T: MaxValue { const MAX : Self = Saturating(T::MAX); }
212
213impl<T, const N : usize> MaxValue for [T;N] where T: MaxValue
214{
215 const MAX : Self = [T::MAX; N];
216}
217
218
219
220
221#[macro_export]
222macro_rules! map_on_constant_unit {
223 ($($macro_arms:tt)*) => {
224 $crate::map_on!
225 (
226 (
227 (Zero, ZERO),
228 (NaNValue, NAN),
229 (MinValue, MIN),
230 (MaxValue, MAX)
231 ),
232 $($macro_arms)*
233 );
234 };
235}
236
237#[macro_export]
238macro_rules! map_on_constant {
239 ($($macro_arms:tt)*) => {
240 $crate::map_on!
241 (
242 (
243 (Zero, ZERO),
244 (One, ONE),
245 (MinusOne, MINUS_ONE),
246 (Half, HALF),
247 (NaNValue, NAN),
248 (MinValue, MIN),
249 (MaxValue, MAX)
250 ),
251 $($macro_arms)*
252 );
253 };
254}