spirix/constants/
circle.rs

1use super::ExponentConstants;
2use super::FractionConstants;
3use crate::Circle;
4pub trait CircleConstants {
5    /// Maximum finite value that can be represented by this type of Circle.
6    const MAX: Self;
7    /// Minimum finite value that can be represented by this type of Circle.
8    const MIN: Self;
9    /// The smallest positive value that can be represented by this type of Circle.
10    const MIN_POS: Self;
11    /// Smallest magnitude negative value that can be represented by this type of Circle.
12    const MAX_NEG: Self;
13    /// Granularity between 1 and 2
14    const POS_NORMAL_EPSILON: Self;
15    /// Granularity between -1 and -2
16    const NEG_NORMAL_EPSILON: Self;
17    /// The maximum value that maintains integer contiguity with its neighboring values.
18    /// This is one less than MAX_FRACTION to ensure the value connects to both its
19    /// predecessor and successor in the representable sequence (a+1!=a).
20    const MAX_CONTIGUOUS: Self;
21    /// The minimum value that maintains integer contiguity with its neighboring values.
22    /// This is one more than MIN_FRACTION to ensure the value connects to both its
23    /// predecessor and successor in the representable sequence (a-1!=a).
24    const MIN_CONTIGUOUS: Self;
25    /// Actual Zero, the real deal. Exploded * 0 = 0
26    const ZERO: Self;
27    /// Mathematical infinity - the result of division by Zero (1/0).
28    /// Unlike IEEE-754's signed infinities, this represents a singular infinity
29    /// where the sign is indeterminate. Represented by all fraction bits set (11111111)
30    /// with an ambiguous exponent, creating symmetry with ZERO (00000000).
31    /// Used for results where magnitude is infinite and direction is ambiguous.
32    const INFINITY: Self;
33    /// Exactly one.
34    const ONE: Self;
35    /// Exactly negative one.
36    const NEG_ONE: Self;
37    /// Effectively one (the largest value smaller than one).
38    const EFFECTIVELY_POS_ONE: Self;
39    /// Effectively negative one (the closest value to -1 with magnitude less than 1).
40    const EFFECTIVELY_NEG_ONE: Self;
41    /// Exactly two.
42    const TWO: Self;
43    /// Exactly 1/2.
44    const HALF: Self;
45    /// The imaginary unit (i).
46    const POS_I: Self;
47    /// Negative imaginary unit (-i).
48    const NEG_I: Self;
49    /// Approximately Pi (π ≈ 3.14159265358979323846...)
50    const PI: Self;
51    /// Approximately negative Pi (-π ≈ -3.14159265358979323846...)
52    const NEG_PI: Self;
53    /// Approximately Tau (2π ≈ 6.28318530717958647693...)
54    const TAU: Self;
55    /// Approximately negative Tau (-2π ≈ -6.28318530717958647693...)
56    const NEG_TAU: Self;
57    /// Alternative name for TAU (2π)
58    const TWO_PI: Self;
59    /// Pi divided by two (π/2 ≈ 1.57079632679489661923...)
60    const PI_OVER_TWO: Self;
61    /// Negative Pi divided by two (-π/2 ≈ -1.57079632679489661923...)
62    const NEG_PI_OVER_TWO: Self;
63    /// Pi divided by three (π/3 ≈ 1.04719755119659774615...)
64    const PI_OVER_THREE: Self;
65    /// Pi divided by four (π/4 ≈ 0.78539816339744830962...)
66    const PI_OVER_FOUR: Self;
67    /// Pi divided by six (π/6 ≈ 0.52359877559829887308...)
68    const PI_OVER_SIX: Self;
69    /// Pi divided by eight (π/8 ≈ 0.39269908169872415481...)
70    const PI_OVER_EIGHT: Self;
71    /// One divided by pi (1/π ≈ 0.31830988618379067154...)
72    const ONE_OVER_PI: Self;
73    /// Two divided by pi (2/π ≈ 0.63661977236758134308...)
74    const TWO_OVER_PI: Self;
75    /// Approximately Euler's number (e ≈ 2.71828182845904523536...)
76    const E: Self;
77    /// Approximately natural logarithm of two (ln(2) ≈ 0.69314718055994530942...)
78    const LN_TWO: Self;
79    /// Binary logarithm of e (log(e,2) ≈ 1.44269504088896340736...)
80    const LB_E: Self;
81    /// Approximately square root of two (√2 ≈ 1.41421356237309504880...)
82    const SQRT_TWO: Self;
83}
84macro_rules! impl_circle_constants {
85    ($($f:ty, $e:ty);*) => {
86        $(
87 impl Circle<$f, $e> {
88    /// Maximum finite value that can be represented by this type of Circle.
89    pub const MAX: Self = Self {
90        real: <$f>::MAX_FRACTION,
91        imaginary: 0,
92        exponent: <$e>::MAX_EXPONENT,
93    };
94    /// Minimum finite value that can be represented by this type of Circle.
95    pub const MIN: Self = Self {
96        real: <$f>::MIN_FRACTION,
97        imaginary: 0,
98        exponent: <$e>::MAX_EXPONENT,
99    };
100    /// The smallest positive value that can be represented by this type of Circle.
101    pub const MIN_POS: Self = Self {
102        real: <$f>::POS_ONE_FRACTION,
103        imaginary: 0,
104        exponent: <$e>::MIN_EXPONENT,
105    };
106    /// Smallest magnitude negative value that can be represented by this type of Circle.
107    pub const MAX_NEG: Self = Self {
108        real: <$f>::NEG_ONE_FRACTION,
109        imaginary: 0,
110        exponent: <$e>::MIN_EXPONENT,
111    };
112    /// Granularity between 1/2 and 1
113    pub const POS_NORMAL_EPSILON: Self = Self {
114        real: <$f>::POS_ONE_FRACTION,
115        imaginary: 0,
116        exponent: (2isize.wrapping_sub(<$f>::FRACTION_BITS as isize)) as $e,
117    };
118    /// Granularity between -1 and -1/2
119    pub const NEG_NORMAL_EPSILON: Self = Self {
120        real: <$f>::NEG_ONE_FRACTION,
121        imaginary: 0,
122        exponent: (1isize.wrapping_sub(<$f>::FRACTION_BITS as isize)) as $e,
123    };
124    /// The maximum value that maintains integer contiguity with its neighboring values.
125    /// This is one less than MAX_FRACTION to ensure the value connects to both its
126    /// predecessor and successor in the representable sequence (a+1!=a).
127    pub const MAX_CONTIGUOUS: Self = Self {
128        real: <$f>::MAX_FRACTION.wrapping_sub(1),
129        imaginary: 0,
130        exponent: ((<$e>::FRACTION_BITS).wrapping_add(<$e>::EXPONENT_BITS).wrapping_sub(1)) as $e,
131    };
132    /// The minimum value that maintains integer contiguity with its neighboring values.
133    /// This is one more than MIN_FRACTION to ensure the value connects to both its
134    /// predecessor and successor in the representable sequence (a-1!=a).
135    pub const MIN_CONTIGUOUS: Self = Self {
136        real: <$f>::MIN_FRACTION.wrapping_add(1),
137        imaginary: 0,
138        exponent: ((<$e>::FRACTION_BITS).wrapping_add(<$e>::EXPONENT_BITS).wrapping_sub(1)) as $e,
139    };
140    /// Actual Zero, the real deal. Exploded * 0 = 0
141    pub const ZERO: Self = Self {
142        real: 0,
143        imaginary: 0,
144        exponent: <$e>::AMBIGUOUS_EXPONENT,
145    };
146    /// Mathematical infinity - the result of division by Zero (1/0).
147    /// Unlike IEEE-754's signed infinities, this represents a singular infinity
148    /// where the sign is indeterminate. Represented by all fraction bits set (11111111)
149    /// with an ambiguous exponent, creating symmetry with ZERO (00000000).
150    /// Used for results where magnitude is infinite and direction is ambiguous.
151    pub const INFINITY: Self = Self {
152        real: -1,
153        imaginary: -1,
154        exponent: <$e>::AMBIGUOUS_EXPONENT,
155    };
156    /// Exactly one.
157    pub const ONE: Self = Self {
158        real: <$f>::POS_ONE_FRACTION,
159        imaginary: 0,
160        exponent: 1,
161    };
162    /// Exactly negative one.
163    pub const NEG_ONE: Self = Self {
164        real: <$f>::MIN_FRACTION,
165        imaginary: 0,
166        exponent: 0,
167    };
168    /// Effectively one (the largest value smaller than one).
169    pub const EFFECTIVELY_POS_ONE: Self = Self {
170        real: <$f>::MAX_FRACTION,
171        imaginary: 0,
172        exponent: 0,
173    };
174    /// Effectively negative one (the closest value to -1 with magnitude less than 1).
175    pub const EFFECTIVELY_NEG_ONE: Self = Self {
176        real: <$f>::MIN_FRACTION.wrapping_add(1),
177        imaginary: 0,
178        exponent: 0,
179    };
180    /// Exactly two.
181    pub const TWO: Self = Self {
182        real: <$f>::POS_ONE_FRACTION,
183        imaginary: 0,
184        exponent: 2,
185    };
186    /// Exactly 1/2.
187    pub const HALF: Self = Self {
188        real: <$f>::POS_ONE_FRACTION,
189        imaginary: 0,
190        exponent: 0,
191    };
192    /// Imaginary unit (i).
193    pub const POS_I: Self = Self {
194        real: 0,
195        imaginary: <$f>::POS_ONE_FRACTION,
196        exponent: 1,
197    };
198    /// Negative imaginary unit (-i).
199    pub const NEG_I: Self = Self {
200        real: 0,
201        imaginary: <$f>::MIN_FRACTION,
202        exponent: 0,
203    };
204    /// Approximately Pi (π ≈ 3.14159265358979323846...)
205    pub const PI: Self = Self {
206        real: (0x6487ED5110B4611A62633145C06E0E69i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
207        imaginary: 0,
208        exponent: 2,
209    };
210    /// Approximately negative Pi (-π ≈ -3.14159265358979323846...)
211    pub const NEG_PI: Self = Self {
212        real: (-0x6487ED5110B4611A62633145C06E0E69i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
213        imaginary: 0,
214        exponent: 2,
215    };
216    /// Approximately Tau (2π ≈ 6.28318530717958647693...)
217    pub const TAU: Self = Self {
218        real: (0x6487ED5110B4611A62633145C06E0E69i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
219        imaginary: 0,
220        exponent: 3,
221    };
222    /// Approximately negative Tau (-2π ≈ -6.28318530717958647693...)
223    pub const NEG_TAU: Self = Self {
224        real: (-0x6487ED5110B4611A62633145C06E0E68i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
225        imaginary: 0,
226        exponent: 3,
227    };
228    /// Alternative name for TAU (2π)
229    pub const TWO_PI: Self = Self::TAU;
230    /// Pi divided by two (π/2 ≈ 1.57079632679489661923...)
231    pub const PI_OVER_TWO: Self = Self {
232        real: (0x6487ED5110B4611A62633145C06E0E69i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
233        imaginary: 0,
234        exponent: 1,
235    };
236    /// Negative Pi divided by two (-π/2 ≈ -1.57079632679489661923...)
237    pub const NEG_PI_OVER_TWO: Self = Self {
238        real: (-0x6487ED5110B4611A62633145C06E0E68i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
239        imaginary: 0,
240        exponent: 1,
241    };
242    /// Pi divided by three (π/3 ≈ 1.04719755119659774615...)
243    pub const PI_OVER_THREE: Self = Self {
244        real: (0x430548E0B5CD961196ECCB83D59EB446i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
245        imaginary: 0,
246        exponent: 1,
247    };
248    /// Pi divided by four (π/4 ≈ 0.78539816339744830962...)
249    pub const PI_OVER_FOUR: Self = Self {
250        real: (0x6487ED5110B4611A62633145C06E0E69i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
251        imaginary: 0,
252        exponent: 0,
253    };
254    /// Pi divided by six (π/6 ≈ 0.52359877559829887308...)
255    pub const PI_OVER_SIX: Self = Self {
256        real: (0x430548E0B5CD961196ECCB83D59EB446i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
257        imaginary: 0,
258        exponent: 0,
259    };
260    /// Pi divided by eight (π/8 ≈ 0.39269908169872415481...)
261    pub const PI_OVER_EIGHT: Self = Self {
262        real: (0x6487ED5110B4611A62633145C06E0E69i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
263        imaginary: 0,
264        exponent: -1,
265    };
266    /// One divided by pi (1/π ≈ 0.31830988618379067154...)
267    pub const ONE_OVER_PI: Self = Self {
268        real: (0x517CC1B727220A94FE13ABE8FA9A6EE0i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
269        imaginary: 0,
270        exponent: -1,
271    };
272    /// Two divided by pi (2/π ≈ 0.63661977236758134308...)
273    pub const TWO_OVER_PI: Self = Self {
274        real: (0x517CC1B727220A94FE13ABE8FA9A6EE0i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
275        imaginary: 0,
276        exponent: 0,
277    };
278    /// Approximately Euler's number (e ≈ 2.71828182845904523536...)
279    pub const E: Self = Self {
280        real: (0x56FC2A2C515DA54D57EE2B10139E9E79i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
281        imaginary: 0,
282        exponent: 2,
283    };
284    /// Approximately natural logarithm of two (ln(2) ≈ 0.69314718055994530942...)
285    pub const LN_TWO: Self = Self {
286        real: (0x58B90BFBE8E7BCD5E4F1D9CC01F97B57i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
287        imaginary: 0,
288        exponent: 0,
289    };
290    /// Binary logarithm of e (log₂(e) ≈ 1.44269504088896340736...)
291    pub const LB_E: Self = Self {
292        real: (0x5C551D94AE0BF85DDF43FF68348E9F44i128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
293        imaginary: 0,
294        exponent: 1,
295    };
296    /// Approximately square root of two (√2 ≈ 1.41421356237309504880...)
297    pub const SQRT_TWO: Self = Self {
298        real: (0x5A827999FCEF32422CBEC4D9BAA55F4Fi128 >> (128isize.wrapping_sub(<$f>::FRACTION_BITS))) as $f,
299        imaginary: 0,
300        exponent: 1,
301    };
302}
303
304        impl CircleConstants for Circle<$f, $e> {
305            const MAX: Self = Self::MAX;
306            const MIN: Self = Self::MIN;
307            const MIN_POS: Self = Self::MIN_POS;
308            const MAX_NEG: Self = Self::MAX_NEG;
309            const POS_NORMAL_EPSILON: Self = Self::POS_NORMAL_EPSILON;
310            const NEG_NORMAL_EPSILON: Self = Self::NEG_NORMAL_EPSILON;
311            const MAX_CONTIGUOUS: Self = Self::MAX_CONTIGUOUS;
312            const MIN_CONTIGUOUS: Self = Self::MIN_CONTIGUOUS;
313            const ZERO: Self = Self::ZERO;
314            const INFINITY: Self = Self::INFINITY;
315            const ONE: Self = Self::ONE;
316            const NEG_ONE: Self = Self::NEG_ONE;
317            const EFFECTIVELY_POS_ONE: Self = Self::EFFECTIVELY_POS_ONE;
318            const EFFECTIVELY_NEG_ONE: Self = Self::EFFECTIVELY_NEG_ONE;
319            const TWO: Self = Self::TWO;
320            const HALF: Self = Self::HALF;
321            const POS_I: Self = Self::POS_I;
322            const NEG_I: Self = Self::NEG_I;
323            const PI: Self = Self::PI;
324            const NEG_PI: Self = Self::NEG_PI;
325            const TAU: Self = Self::TAU;
326            const NEG_TAU: Self = Self::NEG_TAU;
327            const TWO_PI: Self = Self::TWO_PI;
328            const PI_OVER_TWO: Self = Self::PI_OVER_TWO;
329            const NEG_PI_OVER_TWO: Self = Self::NEG_PI_OVER_TWO;
330            const PI_OVER_THREE: Self = Self::PI_OVER_THREE;
331            const PI_OVER_FOUR: Self = Self::PI_OVER_FOUR;
332            const PI_OVER_SIX: Self = Self::PI_OVER_SIX;
333            const PI_OVER_EIGHT: Self = Self::PI_OVER_EIGHT;
334            const ONE_OVER_PI: Self = Self::ONE_OVER_PI;
335            const TWO_OVER_PI: Self = Self::TWO_OVER_PI;
336            const E: Self = Self::E;
337            const LN_TWO: Self = Self::LN_TWO;
338            const LB_E: Self = Self::LB_E;
339            const SQRT_TWO: Self = Self::SQRT_TWO;
340        }
341    )*
342}
343}
344impl_circle_constants!(
345   i8, i8;
346   i16, i8;
347   i32, i8;
348   i64, i8;
349   i128, i8;
350   i8, i16;
351   i16, i16;
352   i32, i16;
353   i64, i16;
354   i128, i16;
355   i8, i32;
356   i16, i32;
357   i32, i32;
358   i64, i32;
359   i128, i32;
360   i8, i64;
361   i16, i64;
362   i32, i64;
363   i64, i64;
364   i128, i64;
365   i8, i128;
366   i16, i128;
367   i32, i128;
368   i64, i128;
369   i128, i128
370);