1#![cfg_attr(docsrs, feature(doc_cfg))]
4#![no_std]
5#![doc(test(attr(deny(warnings))))]
6
7#[cfg(all(feature = "alloc", any(feature = "serde", feature = "quickcheck")))]
8extern crate alloc;
9
10#[cfg(test)]
11mod tests;
12mod unsafe_wrapper;
13
14use core::borrow::Borrow;
15use core::cmp::Ordering;
16use core::error::Error;
17use core::fmt;
18use core::hint::assert_unchecked;
19use core::num::{IntErrorKind, NonZero};
20use core::str::FromStr;
21
22#[cfg(docsrs)]
39#[doc(cfg(feature = "macros"))]
40#[macro_export]
41macro_rules! int {
42 ($min:literal, $max:literal) => {};
43}
44
45#[cfg(docsrs)]
62#[doc(cfg(feature = "macros"))]
63#[macro_export]
64macro_rules! opt_int {
65 ($min:literal, $max:literal) => {};
66}
67
68#[cfg(all(not(docsrs), feature = "macros"))]
69pub use deranged_macros::int;
70#[cfg(all(not(docsrs), feature = "macros"))]
71pub use deranged_macros::opt_int;
72#[cfg(feature = "powerfmt")]
73use powerfmt::smart_display;
74
75use crate::unsafe_wrapper::Unsafe;
76
77#[derive(Debug, Clone, Copy, PartialEq, Eq)]
79pub struct TryFromIntError;
80
81impl fmt::Display for TryFromIntError {
82 #[inline]
83 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
84 f.write_str("out of range integral type conversion attempted")
85 }
86}
87impl Error for TryFromIntError {}
88
89#[allow(missing_copy_implementations)] #[derive(Debug, Clone, PartialEq, Eq)]
110pub struct ParseIntError {
111 #[allow(clippy::missing_docs_in_private_items)]
112 kind: IntErrorKind,
113}
114
115impl ParseIntError {
116 #[allow(clippy::missing_const_for_fn)]
119 #[inline(always)]
120 pub fn kind(&self) -> &IntErrorKind {
121 &self.kind
122 }
123}
124
125impl fmt::Display for ParseIntError {
126 #[inline]
127 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
128 match self.kind {
129 IntErrorKind::Empty => "cannot parse integer from empty string",
130 IntErrorKind::InvalidDigit => "invalid digit found in string",
131 IntErrorKind::PosOverflow => "number too large to fit in target type",
132 IntErrorKind::NegOverflow => "number too small to fit in target type",
133 IntErrorKind::Zero => "number would be zero for non-zero type",
134 _ => "Unknown Int error kind",
135 }
136 .fmt(f)
137 }
138}
139
140impl Error for ParseIntError {}
141
142macro_rules! const_try_opt {
144 ($e:expr) => {
145 match $e {
146 Some(value) => value,
147 None => return None,
148 }
149 };
150}
151
152macro_rules! if_signed {
154 (true $($x:tt)*) => { $($x)*};
155 (false $($x:tt)*) => {};
156}
157
158macro_rules! if_unsigned {
160 (true $($x:tt)*) => {};
161 (false $($x:tt)*) => { $($x)* };
162}
163
164macro_rules! article {
166 (true) => {
167 "An"
168 };
169 (false) => {
170 "A"
171 };
172}
173
174#[allow(unused_macro_rules)]
176macro_rules! if_not_manual_rand_09 {
177 ([rand_09 $($rest:ident)*] $($output:tt)*) => {};
178 ([] $($output:tt)*) => {
179 $($output)*
180 };
181 ([$first:ident $($rest:ident)*] $($output:tt)*) => {
182 if_not_manual_rand_09!([$($rest)*] $($output)*);
183 };
184}
185
186#[allow(unused_macro_rules)]
188macro_rules! if_not_manual_rand_010 {
189 ([rand_010 $($rest:ident)*] $($output:tt)*) => {};
190 ([] $($output:tt)*) => {
191 $($output)*
192 };
193 ([$first:ident $($rest:ident)*] $($output:tt)*) => {
194 if_not_manual_rand_010!([$($rest)*] $($output)*);
195 };
196}
197
198macro_rules! impl_ranged {
200 ($(
201 $type:ident {
202 mod_name: $mod_name:ident
203 alias: $alias:ident
204 internal: $internal:ident
205 signed: $is_signed:ident
206 unsigned: $unsigned_type:ident
207 optional: $optional_type:ident
208 optional_alias: $optional_alias:ident
209 from: [$($from:ident($from_internal:ident))+]
210 $(manual: [$($skips:ident)+])?
211 }
212 )*) => {$(
213 #[doc = concat!("Equivalent to `", stringify!($type), "`")]
214 #[expect(non_camel_case_types, reason = "symmetry with primitives")]
215 pub type $alias<const MIN: $internal, const MAX: $internal> = $type<MIN, MAX>;
216
217 #[doc = concat!("Equivalent to `", stringify!($optional_type), "`")]
218 #[expect(non_camel_case_types, reason = "closest visually to `Option<T>`")]
219 pub type $optional_alias<const MIN: $internal, const MAX: $internal>
220 = $optional_type<MIN, MAX>;
221
222 #[doc = concat!(
223 article!($is_signed),
224 " `",
225 stringify!($internal),
226 "` that is known to be in the range `MIN..=MAX`.",
227 )]
228 #[repr(transparent)]
229 #[derive(Clone, Copy, Eq, Ord, Hash)]
230 pub struct $type<const MIN: $internal, const MAX: $internal>(
231 Unsafe<$internal>,
232 );
233
234 #[doc = concat!(
235 "An optional `",
236 stringify!($type),
237 "`; similar to `Option<",
238 stringify!($type),
239 ">` with better optimization.",
240 )]
241 #[doc = concat!(
243 "If `MIN` is [`",
244 stringify!($internal),
245 "::MIN`] _and_ `MAX` is [`",
246 stringify!($internal)
247 ,"::MAX`] then compilation will fail. This is because there is no way to represent \
248 the niche value.",
249 )]
250 #[doc = concat!("obtained with [`", stringify!($optional_type), "::get`].")]
256 #[repr(transparent)]
257 #[derive(Clone, Copy, Eq, Hash)]
258 pub struct $optional_type<const MIN: $internal, const MAX: $internal>(
259 $internal,
260 );
261
262 impl $type<0, 0> {
263 #[doc = concat!("A ", stringify!($type), " that is always `VALUE`.")]
264 #[inline(always)]
265 pub const fn exact<const VALUE: $internal>() -> $type<VALUE, VALUE> {
266 unsafe { $type::new_unchecked(VALUE) }
268 }
269 }
270
271 if_unsigned! { $is_signed
272 impl $type<1, { $internal::MAX }> {
273 #[inline(always)]
275 pub const fn from_nonzero(value: NonZero<$internal>) -> Self {
276 unsafe { Self::new_unchecked(value.get()) }
278 }
279
280 #[inline(always)]
282 pub const fn to_nonzero(self) -> NonZero<$internal> {
283 unsafe { NonZero::new_unchecked(self.get()) }
285 }
286 }}
287
288 impl<const MIN: $internal, const MAX: $internal> $type<MIN, MAX> {
289 pub const MIN: Self = Self::new_static::<MIN>();
292
293 pub const MAX: Self = Self::new_static::<MAX>();
296
297 #[track_caller]
303 #[inline(always)]
304 pub const unsafe fn new_unchecked(value: $internal) -> Self {
305 const { assert!(MIN <= MAX); }
306 unsafe {
308 assert_unchecked(MIN <= value && value <= MAX);
309 Self(Unsafe::new(value))
310 }
311 }
312
313 #[doc = concat!("use [`", stringify!($type), "::get_without_hint`].")]
319 #[track_caller]
320 #[inline(always)]
321 pub const fn get(self) -> $internal {
322 const { assert!(MIN <= MAX); }
323 unsafe { assert_unchecked(MIN <= *self.0.get() && *self.0.get() <= MAX) };
325 *self.0.get()
326 }
327
328 #[doc = concat!("The returned value is identical to [`", stringify!($type), "::get`].")]
331 #[inline(always)]
335 pub const fn get_without_hint(self) -> $internal {
336 const { assert!(MIN <= MAX); }
337 *self.0.get()
338 }
339
340 #[track_caller]
341 #[inline(always)]
342 pub(crate) const fn get_ref(&self) -> &$internal {
343 const { assert!(MIN <= MAX); }
344 let value = self.0.get();
345 unsafe { assert_unchecked(MIN <= *value && *value <= MAX) };
347 value
348 }
349
350 #[inline(always)]
352 pub const fn new(value: $internal) -> Option<Self> {
353 const { assert!(MIN <= MAX); }
354 if value < MIN || value > MAX {
355 None
356 } else {
357 Some(unsafe { Self::new_unchecked(value) })
359 }
360 }
361
362 #[inline(always)]
365 pub const fn new_static<const VALUE: $internal>() -> Self {
366 const {
367 assert!(MIN <= VALUE);
368 assert!(VALUE <= MAX);
369 }
370 unsafe { Self::new_unchecked(VALUE) }
372 }
373
374 #[inline]
376 pub const fn new_saturating(value: $internal) -> Self {
377 const { assert!(MIN <= MAX); }
378 if value < MIN {
379 Self::MIN
380 } else if value > MAX {
381 Self::MAX
382 } else {
383 unsafe { Self::new_unchecked(value) }
385 }
386 }
387
388 #[inline(always)]
399 pub const fn emit_range_hint(self) {
400 const { assert!(MIN <= MAX); }
401 let value = self.0.get();
402 unsafe { assert_unchecked(MIN <= *value && *value <= MAX) };
404 }
405
406 #[inline(always)]
409 pub const fn expand<const NEW_MIN: $internal, const NEW_MAX: $internal>(
410 self,
411 ) -> $type<NEW_MIN, NEW_MAX> {
412 const {
413 assert!(MIN <= MAX);
414 assert!(NEW_MIN <= NEW_MAX);
415 assert!(NEW_MIN <= MIN);
416 assert!(NEW_MAX >= MAX);
417 }
418 unsafe { $type::new_unchecked(self.get()) }
420 }
421
422 #[inline(always)]
426 pub const fn narrow<
427 const NEW_MIN: $internal,
428 const NEW_MAX: $internal,
429 >(self) -> Option<$type<NEW_MIN, NEW_MAX>> {
430 const {
431 assert!(MIN <= MAX);
432 assert!(NEW_MIN <= NEW_MAX);
433 assert!(NEW_MIN >= MIN);
434 assert!(NEW_MAX <= MAX);
435 }
436 $type::<NEW_MIN, NEW_MAX>::new(self.get())
437 }
438
439 #[inline(always)]
446 pub const unsafe fn narrow_unchecked<
447 const NEW_MIN: $internal,
448 const NEW_MAX: $internal,
449 >(self) -> $type<NEW_MIN, NEW_MAX> {
450 const {
451 assert!(MIN <= MAX);
452 assert!(NEW_MIN <= NEW_MAX);
453 assert!(NEW_MIN >= MIN);
454 assert!(NEW_MAX <= MAX);
455 }
456 unsafe { $type::new_unchecked(self.get()) }
458 }
459
460 #[doc = concat!("# use deranged::", stringify!($type), ";")]
480 #[doc = concat!(
481 "assert_eq!(",
482 stringify!($type),
483 "::<5, 10>::from_str_radix(\"A\", 16), Ok(",
484 stringify!($type),
485 "::new_static::<10>()));",
486 )]
487 #[inline]
489 pub fn from_str_radix(src: &str, radix: u32) -> Result<Self, ParseIntError> {
490 const { assert!(MIN <= MAX); }
491 match $internal::from_str_radix(src, radix) {
492 Ok(value) if value > MAX => {
493 Err(ParseIntError { kind: IntErrorKind::PosOverflow })
494 }
495 Ok(value) if value < MIN => {
496 Err(ParseIntError { kind: IntErrorKind::NegOverflow })
497 }
498 Ok(value) => Ok(unsafe { Self::new_unchecked(value) }),
501 Err(e) => Err(ParseIntError { kind: e.kind().clone() }),
502 }
503 }
504
505 #[must_use = "this returns the result of the operation, without modifying the original"]
508 #[inline]
509 pub const fn checked_add(self, rhs: $internal) -> Option<Self> {
510 const { assert!(MIN <= MAX); }
511 Self::new(const_try_opt!(self.get().checked_add(rhs)))
512 }
513
514 #[must_use = "this returns the result of the operation, without modifying the original"]
521 #[track_caller]
522 #[inline(always)]
523 pub const unsafe fn unchecked_add(self, rhs: $internal) -> Self {
524 const { assert!(MIN <= MAX); }
525 unsafe {
527 Self::new_unchecked(self.get().unchecked_add(rhs))
528 }
529 }
530
531 #[must_use = "this returns the result of the operation, without modifying the original"]
534 #[inline]
535 pub const fn checked_sub(self, rhs: $internal) -> Option<Self> {
536 const { assert!(MIN <= MAX); }
537 Self::new(const_try_opt!(self.get().checked_sub(rhs)))
538 }
539
540 #[must_use = "this returns the result of the operation, without modifying the original"]
547 #[track_caller]
548 #[inline(always)]
549 pub const unsafe fn unchecked_sub(self, rhs: $internal) -> Self {
550 const { assert!(MIN <= MAX); }
551 unsafe {
553 Self::new_unchecked(self.get().unchecked_sub(rhs))
554 }
555 }
556
557 #[must_use = "this returns the result of the operation, without modifying the original"]
560 #[inline]
561 pub const fn checked_mul(self, rhs: $internal) -> Option<Self> {
562 const { assert!(MIN <= MAX); }
563 Self::new(const_try_opt!(self.get().checked_mul(rhs)))
564 }
565
566 #[must_use = "this returns the result of the operation, without modifying the original"]
573 #[track_caller]
574 #[inline(always)]
575 pub const unsafe fn unchecked_mul(self, rhs: $internal) -> Self {
576 const { assert!(MIN <= MAX); }
577 unsafe {
579 Self::new_unchecked(self.get().unchecked_mul(rhs))
580 }
581 }
582
583 #[must_use = "this returns the result of the operation, without modifying the original"]
586 #[inline]
587 pub const fn checked_div(self, rhs: $internal) -> Option<Self> {
588 const { assert!(MIN <= MAX); }
589 Self::new(const_try_opt!(self.get().checked_div(rhs)))
590 }
591
592 #[must_use = "this returns the result of the operation, without modifying the original"]
600 #[track_caller]
601 #[inline(always)]
602 pub const unsafe fn unchecked_div(self, rhs: $internal) -> Self {
603 const { assert!(MIN <= MAX); }
604 unsafe {
607 Self::new_unchecked(self.get().checked_div(rhs).unwrap_unchecked())
608 }
609 }
610
611 #[must_use = "this returns the result of the operation, without modifying the original"]
614 #[inline]
615 pub const fn checked_div_euclid(self, rhs: $internal) -> Option<Self> {
616 const { assert!(MIN <= MAX); }
617 Self::new(const_try_opt!(self.get().checked_div_euclid(rhs)))
618 }
619
620 #[must_use = "this returns the result of the operation, without modifying the original"]
628 #[track_caller]
629 #[inline(always)]
630 pub const unsafe fn unchecked_div_euclid(self, rhs: $internal) -> Self {
631 const { assert!(MIN <= MAX); }
632 unsafe {
635 Self::new_unchecked(
636 self.get().checked_div_euclid(rhs).unwrap_unchecked()
637 )
638 }
639 }
640
641 if_unsigned!($is_signed
642 #[must_use = "this returns the result of the operation, without modifying the original"]
645 #[track_caller]
646 #[inline]
647 pub const fn rem<const RHS_VALUE: $internal>(
648 self,
649 rhs: $type<RHS_VALUE, RHS_VALUE>,
650 ) -> $type<0, RHS_VALUE> {
651 const { assert!(MIN <= MAX); }
652 unsafe { $type::new_unchecked(self.get() % rhs.get()) }
655 });
656
657 #[must_use = "this returns the result of the operation, without modifying the original"]
660 #[inline]
661 pub const fn checked_rem(self, rhs: $internal) -> Option<Self> {
662 const { assert!(MIN <= MAX); }
663 Self::new(const_try_opt!(self.get().checked_rem(rhs)))
664 }
665
666 #[must_use = "this returns the result of the operation, without modifying the original"]
674 #[track_caller]
675 #[inline(always)]
676 pub const unsafe fn unchecked_rem(self, rhs: $internal) -> Self {
677 const { assert!(MIN <= MAX); }
678 unsafe {
681 Self::new_unchecked(self.get().checked_rem(rhs).unwrap_unchecked())
682 }
683 }
684
685 #[must_use = "this returns the result of the operation, without modifying the original"]
688 #[inline]
689 pub const fn checked_rem_euclid(self, rhs: $internal) -> Option<Self> {
690 const { assert!(MIN <= MAX); }
691 Self::new(const_try_opt!(self.get().checked_rem_euclid(rhs)))
692 }
693
694 #[must_use = "this returns the result of the operation, without modifying the original"]
702 #[track_caller]
703 #[inline(always)]
704 pub const unsafe fn unchecked_rem_euclid(self, rhs: $internal) -> Self {
705 const { assert!(MIN <= MAX); }
706 unsafe {
709 Self::new_unchecked(
710 self.get().checked_rem_euclid(rhs).unwrap_unchecked()
711 )
712 }
713 }
714
715 #[must_use = "this returns the result of the operation, without modifying the original"]
718 #[inline]
719 pub const fn checked_neg(self) -> Option<Self> {
720 const { assert!(MIN <= MAX); }
721 Self::new(const_try_opt!(self.get().checked_neg()))
722 }
723
724 #[must_use = "this returns the result of the operation, without modifying the original"]
730 #[track_caller]
731 #[inline(always)]
732 pub const unsafe fn unchecked_neg(self) -> Self {
733 const { assert!(MIN <= MAX); }
734 unsafe { Self::new_unchecked(self.get().checked_neg().unwrap_unchecked()) }
737 }
738
739 #[must_use = "this returns the result of the operation, without modifying the original"]
742 #[inline(always)]
743 pub const fn neg(self) -> Self {
744 const {
745 assert!(MIN <= MAX);
746 if_signed! { $is_signed
747 assert!(MIN != $internal::MIN);
748 assert!(-MIN <= MAX);
749 assert!(-MAX >= MIN);
750 }
751 if_unsigned! { $is_signed
752 assert!(MAX == 0);
753 }
754 }
755 unsafe { self.unchecked_neg() }
757 }
758
759 #[must_use = "this returns the result of the operation, without modifying the original"]
762 #[inline]
763 pub const fn checked_shl(self, rhs: u32) -> Option<Self> {
764 const { assert!(MIN <= MAX); }
765 Self::new(const_try_opt!(self.get().checked_shl(rhs)))
766 }
767
768 #[must_use = "this returns the result of the operation, without modifying the original"]
774 #[track_caller]
775 #[inline(always)]
776 pub const unsafe fn unchecked_shl(self, rhs: u32) -> Self {
777 const { assert!(MIN <= MAX); }
778 unsafe {
780 Self::new_unchecked(self.get().checked_shl(rhs).unwrap_unchecked())
782 }
783 }
784
785 #[must_use = "this returns the result of the operation, without modifying the original"]
788 #[inline]
789 pub const fn checked_shr(self, rhs: u32) -> Option<Self> {
790 const { assert!(MIN <= MAX); }
791 Self::new(const_try_opt!(self.get().checked_shr(rhs)))
792 }
793
794 #[must_use = "this returns the result of the operation, without modifying the original"]
800 #[track_caller]
801 #[inline(always)]
802 pub const unsafe fn unchecked_shr(self, rhs: u32) -> Self {
803 const { assert!(MIN <= MAX); }
804 unsafe {
806 Self::new_unchecked(self.get().checked_shr(rhs).unwrap_unchecked())
808 }
809 }
810
811 if_signed!($is_signed
812 #[must_use = "this returns the result of the operation, without modifying the original"]
815 #[inline]
816 pub const fn checked_abs(self) -> Option<Self> {
817 const { assert!(MIN <= MAX); }
818 Self::new(const_try_opt!(self.get().checked_abs()))
819 }
820
821 #[must_use = "this returns the result of the operation, without modifying the original"]
828 #[track_caller]
829 #[inline(always)]
830 pub const unsafe fn unchecked_abs(self) -> Self {
831 const { assert!(MIN <= MAX); }
832 unsafe { Self::new_unchecked(self.get().checked_abs().unwrap_unchecked()) }
834 }
835
836 #[must_use = "this returns the result of the operation, without modifying the original"]
839 #[inline(always)]
840 pub const fn abs(self) -> Self {
841 const {
842 assert!(MIN <= MAX);
843 assert!(MIN != $internal::MIN);
844 assert!(-MIN <= MAX);
845 }
846 unsafe { self.unchecked_abs() }
849 });
850
851 #[must_use = "this returns the result of the operation, without modifying the original"]
854 #[inline]
855 pub const fn checked_pow(self, exp: u32) -> Option<Self> {
856 const { assert!(MIN <= MAX); }
857 Self::new(const_try_opt!(self.get().checked_pow(exp)))
858 }
859
860 #[must_use = "this returns the result of the operation, without modifying the original"]
867 #[track_caller]
868 #[inline(always)]
869 pub const unsafe fn unchecked_pow(self, exp: u32) -> Self {
870 const { assert!(MIN <= MAX); }
871 unsafe {
873 Self::new_unchecked(self.get().checked_pow(exp).unwrap_unchecked())
874 }
875 }
876
877 #[must_use = "this returns the result of the operation, without modifying the original"]
880 #[inline]
881 pub const fn saturating_add(self, rhs: $internal) -> Self {
882 const { assert!(MIN <= MAX); }
883 Self::new_saturating(self.get().saturating_add(rhs))
884 }
885
886 #[must_use = "this returns the result of the operation, without modifying the original"]
889 #[inline]
890 pub const fn saturating_sub(self, rhs: $internal) -> Self {
891 const { assert!(MIN <= MAX); }
892 Self::new_saturating(self.get().saturating_sub(rhs))
893 }
894
895 if_signed!($is_signed
896 #[must_use = "this returns the result of the operation, without modifying the original"]
899 #[inline]
900 pub const fn saturating_neg(self) -> Self {
901 const { assert!(MIN <= MAX); }
902 Self::new_saturating(self.get().saturating_neg())
903 });
904
905 if_signed!($is_signed
906 #[must_use = "this returns the result of the operation, without modifying the original"]
908 #[inline]
909 pub const fn saturating_abs(self) -> Self {
910 const { assert!(MIN <= MAX); }
911 Self::new_saturating(self.get().saturating_abs())
912 });
913
914 #[must_use = "this returns the result of the operation, without modifying the original"]
917 #[inline]
918 pub const fn saturating_mul(self, rhs: $internal) -> Self {
919 const { assert!(MIN <= MAX); }
920 Self::new_saturating(self.get().saturating_mul(rhs))
921 }
922
923 #[must_use = "this returns the result of the operation, without modifying the original"]
926 #[inline]
927 pub const fn saturating_pow(self, exp: u32) -> Self {
928 const { assert!(MIN <= MAX); }
929 Self::new_saturating(self.get().saturating_pow(exp))
930 }
931
932 if_signed! { $is_signed
933 #[inline]
936 pub const fn is_positive(self) -> bool {
937 const { assert!(MIN <= MAX); }
938 self.get().is_positive()
939 }
940
941 #[inline]
944 pub const fn is_negative(self) -> bool {
945 const { assert!(MIN <= MAX); }
946 self.get().is_negative()
947 }
948 }
949
950 #[must_use = "this returns the result of the operation, without modifying the original"]
954 #[track_caller]
955 #[inline]
956 #[allow(trivial_numeric_casts)] const fn rem_euclid_unsigned(
958 rhs: $internal,
959 range_len: $unsigned_type
960 ) -> $unsigned_type {
961 #[allow(unused_comparisons)]
962 if rhs >= 0 {
963 (rhs as $unsigned_type) % range_len
964 } else {
965 let rhs_abs = ($internal::wrapping_sub(0, rhs)) as $unsigned_type;
969 ((($unsigned_type::MAX / range_len) * range_len) - (rhs_abs)) % range_len
976 }
977 }
978
979 #[must_use = "this returns the result of the operation, without modifying the original"]
982 #[inline]
983 #[allow(trivial_numeric_casts)] pub const fn wrapping_add(self, rhs: $internal) -> Self {
985 const { assert!(MIN <= MAX); }
986 if MIN == $internal::MIN && MAX == $internal::MAX {
988 return unsafe { Self::new_unchecked(self.get().wrapping_add(rhs)) }
990 }
991
992 let inner = self.get();
993
994 let range_len = MAX.abs_diff(MIN) + 1;
996
997 let offset = Self::rem_euclid_unsigned(rhs, range_len);
999
1000 let greater_vals = MAX.abs_diff(inner);
1001 if offset <= greater_vals {
1003 unsafe { Self::new_unchecked(
1011 ((inner as $unsigned_type).wrapping_add(offset)) as $internal
1012 ) }
1013 }
1014 else {
1016 unsafe { Self::new_unchecked(
1022 ((MIN as $unsigned_type).wrapping_add(
1023 offset - (greater_vals + 1)
1024 )) as $internal
1025 ) }
1026 }
1027 }
1028
1029 #[must_use = "this returns the result of the operation, without modifying the original"]
1032 #[inline]
1033 #[allow(trivial_numeric_casts)] pub const fn wrapping_sub(self, rhs: $internal) -> Self {
1035 const { assert!(MIN <= MAX); }
1036 if MIN == $internal::MIN && MAX == $internal::MAX {
1038 return unsafe { Self::new_unchecked(self.get().wrapping_sub(rhs)) }
1040 }
1041
1042 let inner = self.get();
1043
1044 let range_len = MAX.abs_diff(MIN) + 1;
1046
1047 let offset = Self::rem_euclid_unsigned(rhs, range_len);
1049
1050 let lesser_vals = MIN.abs_diff(inner);
1051 if offset <= lesser_vals {
1053 unsafe { Self::new_unchecked(
1061 ((inner as $unsigned_type).wrapping_sub(offset)) as $internal
1062 ) }
1063 }
1064 else {
1066 unsafe { Self::new_unchecked(
1072 ((MAX as $unsigned_type).wrapping_sub(
1073 offset - (lesser_vals + 1)
1074 )) as $internal
1075 ) }
1076 }
1077 }
1078 }
1079
1080 impl<const MIN: $internal, const MAX: $internal> $optional_type<MIN, MAX> {
1081 const NICHE: $internal = match (MIN, MAX) {
1083 ($internal::MIN, $internal::MAX) => panic!("type has no niche"),
1084 ($internal::MIN, _) => $internal::MAX,
1085 (_, _) => $internal::MIN,
1086 };
1087
1088 #[allow(non_upper_case_globals)]
1090 pub const None: Self = Self(Self::NICHE);
1091
1092 #[allow(non_snake_case)]
1094 #[inline(always)]
1095 pub const fn Some(value: $type<MIN, MAX>) -> Self {
1096 const { assert!(MIN <= MAX); }
1097 Self(value.get())
1098 }
1099
1100 #[inline(always)]
1102 pub const fn get(self) -> Option<$type<MIN, MAX>> {
1103 const { assert!(MIN <= MAX); }
1104 if self.0 == Self::NICHE {
1105 None
1106 } else {
1107 Some(unsafe { $type::new_unchecked(self.0) })
1109 }
1110 }
1111
1112 #[inline(always)]
1120 #[track_caller]
1121 pub const unsafe fn some_unchecked(value: $internal) -> Self {
1122 const { assert!(MIN <= MAX); }
1123 unsafe { assert_unchecked(MIN <= value && value <= MAX) };
1125 Self(value)
1126 }
1127
1128 #[inline(always)]
1130 pub(crate) const fn inner(self) -> $internal {
1131 const { assert!(MIN <= MAX); }
1132 self.0
1133 }
1134
1135 #[doc = concat!(
1141 "use [`", stringify!($optional_type), "::get_primitive_without_hint`]."
1142 )]
1143 #[inline(always)]
1144 pub const fn get_primitive(self) -> Option<$internal> {
1145 const { assert!(MIN <= MAX); }
1146 Some(const_try_opt!(self.get()).get())
1147 }
1148
1149 #[doc = concat!(
1152 "The returned value is identical to [`", stringify!($optional_type), "::",
1153 "get_primitive`]."
1154 )]
1155 #[inline(always)]
1159 pub const fn get_primitive_without_hint(self) -> Option<$internal> {
1160 const { assert!(MIN <= MAX); }
1161 Some(const_try_opt!(self.get()).get_without_hint())
1162 }
1163
1164 #[inline(always)]
1166 pub const fn is_none(&self) -> bool {
1167 const { assert!(MIN <= MAX); }
1168 self.get().is_none()
1169 }
1170
1171 #[inline(always)]
1173 pub const fn is_some(&self) -> bool {
1174 const { assert!(MIN <= MAX); }
1175 self.get().is_some()
1176 }
1177 }
1178
1179 impl<const MIN: $internal, const MAX: $internal> fmt::Debug for $type<MIN, MAX> {
1180 #[inline(always)]
1181 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1182 const { assert!(MIN <= MAX); }
1183 self.get().fmt(f)
1184 }
1185 }
1186
1187 impl<const MIN: $internal, const MAX: $internal> fmt::Debug for $optional_type<MIN, MAX> {
1188 #[inline(always)]
1189 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1190 const { assert!(MIN <= MAX); }
1191 self.get().fmt(f)
1192 }
1193 }
1194
1195 impl<const MIN: $internal, const MAX: $internal> fmt::Display for $type<MIN, MAX> {
1196 #[inline(always)]
1197 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1198 const { assert!(MIN <= MAX); }
1199 self.get().fmt(f)
1200 }
1201 }
1202
1203 #[cfg(feature = "powerfmt")]
1204 impl<
1205 const MIN: $internal,
1206 const MAX: $internal,
1207 > smart_display::SmartDisplay for $type<MIN, MAX> {
1208 type Metadata = <$internal as smart_display::SmartDisplay>::Metadata;
1209
1210 #[inline(always)]
1211 fn metadata(
1212 &self,
1213 f: smart_display::FormatterOptions,
1214 ) -> smart_display::Metadata<'_, Self> {
1215 const { assert!(MIN <= MAX); }
1216 self.get_ref().metadata(f).reuse()
1217 }
1218
1219 #[inline(always)]
1220 fn fmt_with_metadata(
1221 &self,
1222 f: &mut fmt::Formatter<'_>,
1223 metadata: smart_display::Metadata<'_, Self>,
1224 ) -> fmt::Result {
1225 const { assert!(MIN <= MAX); }
1226 self.get().fmt_with_metadata(f, metadata.reuse())
1227 }
1228 }
1229
1230 impl<const MIN: $internal, const MAX: $internal> Default for $optional_type<MIN, MAX> {
1231 #[inline(always)]
1232 fn default() -> Self {
1233 const { assert!(MIN <= MAX); }
1234 Self::None
1235 }
1236 }
1237
1238 impl<const MIN: $internal, const MAX: $internal> AsRef<$internal> for $type<MIN, MAX> {
1239 #[inline(always)]
1240 fn as_ref(&self) -> &$internal {
1241 const { assert!(MIN <= MAX); }
1242 &self.get_ref()
1243 }
1244 }
1245
1246 impl<const MIN: $internal, const MAX: $internal> Borrow<$internal> for $type<MIN, MAX> {
1247 #[inline(always)]
1248 fn borrow(&self) -> &$internal {
1249 const { assert!(MIN <= MAX); }
1250 &self.get_ref()
1251 }
1252 }
1253
1254 impl<
1255 const MIN_A: $internal,
1256 const MAX_A: $internal,
1257 const MIN_B: $internal,
1258 const MAX_B: $internal,
1259 > PartialEq<$type<MIN_B, MAX_B>> for $type<MIN_A, MAX_A> {
1260 #[inline(always)]
1261 fn eq(&self, other: &$type<MIN_B, MAX_B>) -> bool {
1262 const {
1263 assert!(MIN_A <= MAX_A);
1264 assert!(MIN_B <= MAX_B);
1265 }
1266 self.get() == other.get()
1267 }
1268 }
1269
1270 impl<
1271 const MIN_A: $internal,
1272 const MAX_A: $internal,
1273 const MIN_B: $internal,
1274 const MAX_B: $internal,
1275 > PartialEq<$optional_type<MIN_B, MAX_B>> for $optional_type<MIN_A, MAX_A> {
1276 #[inline(always)]
1277 fn eq(&self, other: &$optional_type<MIN_B, MAX_B>) -> bool {
1278 const {
1279 assert!(MIN_A <= MAX_A);
1280 assert!(MIN_B <= MAX_B);
1281 }
1282 self.inner() == other.inner()
1283 }
1284 }
1285
1286 impl<
1287 const MIN_A: $internal,
1288 const MAX_A: $internal,
1289 const MIN_B: $internal,
1290 const MAX_B: $internal,
1291 > PartialOrd<$type<MIN_B, MAX_B>> for $type<MIN_A, MAX_A> {
1292 #[inline(always)]
1293 fn partial_cmp(&self, other: &$type<MIN_B, MAX_B>) -> Option<Ordering> {
1294 const {
1295 assert!(MIN_A <= MAX_A);
1296 assert!(MIN_B <= MAX_B);
1297 }
1298 self.get().partial_cmp(&other.get())
1299 }
1300 }
1301
1302 impl<
1303 const MIN_A: $internal,
1304 const MAX_A: $internal,
1305 const MIN_B: $internal,
1306 const MAX_B: $internal,
1307 > PartialOrd<$optional_type<MIN_B, MAX_B>> for $optional_type<MIN_A, MAX_A> {
1308 #[inline]
1309 fn partial_cmp(&self, other: &$optional_type<MIN_B, MAX_B>) -> Option<Ordering> {
1310 const {
1311 assert!(MIN_A <= MAX_A);
1312 assert!(MIN_B <= MAX_B);
1313 }
1314 if self.is_none() && other.is_none() {
1315 Some(Ordering::Equal)
1316 } else if self.is_none() {
1317 Some(Ordering::Less)
1318 } else if other.is_none() {
1319 Some(Ordering::Greater)
1320 } else {
1321 self.inner().partial_cmp(&other.inner())
1322 }
1323 }
1324 }
1325
1326 impl<
1327 const MIN: $internal,
1328 const MAX: $internal,
1329 > Ord for $optional_type<MIN, MAX> {
1330 #[inline]
1331 fn cmp(&self, other: &Self) -> Ordering {
1332 const { assert!(MIN <= MAX); }
1333 if self.is_none() && other.is_none() {
1334 Ordering::Equal
1335 } else if self.is_none() {
1336 Ordering::Less
1337 } else if other.is_none() {
1338 Ordering::Greater
1339 } else {
1340 self.inner().cmp(&other.inner())
1341 }
1342 }
1343 }
1344
1345 impl<const MIN: $internal, const MAX: $internal> fmt::Binary for $type<MIN, MAX> {
1346 #[inline(always)]
1347 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1348 const { assert!(MIN <= MAX); }
1349 self.get().fmt(f)
1350 }
1351 }
1352
1353 impl<const MIN: $internal, const MAX: $internal> fmt::LowerHex for $type<MIN, MAX> {
1354 #[inline(always)]
1355 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1356 const { assert!(MIN <= MAX); }
1357 self.get().fmt(f)
1358 }
1359 }
1360
1361 impl<const MIN: $internal, const MAX: $internal> fmt::UpperHex for $type<MIN, MAX> {
1362 #[inline(always)]
1363 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1364 const { assert!(MIN <= MAX); }
1365 self.get().fmt(f)
1366 }
1367 }
1368
1369 impl<const MIN: $internal, const MAX: $internal> fmt::LowerExp for $type<MIN, MAX> {
1370 #[inline(always)]
1371 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1372 const { assert!(MIN <= MAX); }
1373 self.get().fmt(f)
1374 }
1375 }
1376
1377 impl<const MIN: $internal, const MAX: $internal> fmt::UpperExp for $type<MIN, MAX> {
1378 #[inline(always)]
1379 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1380 const { assert!(MIN <= MAX); }
1381 self.get().fmt(f)
1382 }
1383 }
1384
1385 impl<const MIN: $internal, const MAX: $internal> fmt::Octal for $type<MIN, MAX> {
1386 #[inline(always)]
1387 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1388 const { assert!(MIN <= MAX); }
1389 self.get().fmt(f)
1390 }
1391 }
1392
1393 if_unsigned! { $is_signed
1394 impl From<NonZero<$internal>> for $type<1, { $internal::MAX }> {
1395 #[inline(always)]
1396 fn from(value: NonZero<$internal>) -> Self {
1397 Self::from_nonzero(value)
1398 }
1399 }
1400
1401 impl From<$type<1, { $internal::MAX }>> for NonZero<$internal> {
1402 #[inline(always)]
1403 fn from(value: $type<1, { $internal::MAX }>) -> Self {
1404 value.to_nonzero()
1405 }
1406 }
1407 }
1408
1409 impl<const MIN: $internal, const MAX: $internal> From<$type<MIN, MAX>> for $internal {
1410 #[inline(always)]
1411 fn from(value: $type<MIN, MAX>) -> Self {
1412 const { assert!(MIN <= MAX); }
1413 value.get()
1414 }
1415 }
1416
1417 impl<
1418 const MIN: $internal,
1419 const MAX: $internal,
1420 > From<$type<MIN, MAX>> for $optional_type<MIN, MAX> {
1421 #[inline(always)]
1422 fn from(value: $type<MIN, MAX>) -> Self {
1423 const { assert!(MIN <= MAX); }
1424 Self::Some(value)
1425 }
1426 }
1427
1428 impl<
1429 const MIN: $internal,
1430 const MAX: $internal,
1431 > From<Option<$type<MIN, MAX>>> for $optional_type<MIN, MAX> {
1432 #[inline(always)]
1433 fn from(value: Option<$type<MIN, MAX>>) -> Self {
1434 const { assert!(MIN <= MAX); }
1435 match value {
1436 Some(value) => Self::Some(value),
1437 None => Self::None,
1438 }
1439 }
1440 }
1441
1442 impl<
1443 const MIN: $internal,
1444 const MAX: $internal,
1445 > From<$optional_type<MIN, MAX>> for Option<$type<MIN, MAX>> {
1446 #[inline(always)]
1447 fn from(value: $optional_type<MIN, MAX>) -> Self {
1448 const { assert!(MIN <= MAX); }
1449 value.get()
1450 }
1451 }
1452
1453 impl<const MIN: $internal, const MAX: $internal> TryFrom<$internal> for $type<MIN, MAX> {
1454 type Error = TryFromIntError;
1455
1456 #[inline]
1457 fn try_from(value: $internal) -> Result<Self, Self::Error> {
1458 const { assert!(MIN <= MAX); }
1459 Self::new(value).ok_or(TryFromIntError)
1460 }
1461 }
1462
1463 impl<const MIN: $internal, const MAX: $internal> FromStr for $type<MIN, MAX> {
1464 type Err = ParseIntError;
1465
1466 #[inline]
1467 fn from_str(s: &str) -> Result<Self, Self::Err> {
1468 const { assert!(MIN <= MAX); }
1469 let value = s.parse::<$internal>().map_err(|e| ParseIntError {
1470 kind: e.kind().clone()
1471 })?;
1472 if value < MIN {
1473 Err(ParseIntError { kind: IntErrorKind::NegOverflow })
1474 } else if value > MAX {
1475 Err(ParseIntError { kind: IntErrorKind::PosOverflow })
1476 } else {
1477 Ok(unsafe { Self::new_unchecked(value) })
1479 }
1480 }
1481 }
1482
1483 $(impl<
1484 const MIN_SRC: $from_internal,
1485 const MAX_SRC: $from_internal,
1486 const MIN_DST: $internal,
1487 const MAX_DST: $internal,
1488 > From<$from<MIN_SRC, MAX_SRC>> for $type<MIN_DST, MAX_DST>
1489 {
1490 #[inline(always)]
1491 #[allow(trivial_numeric_casts, unused_comparisons)]
1492 fn from(value: $from<MIN_SRC, MAX_SRC>) -> Self {
1493 const {
1494 assert!(MIN_SRC <= MAX_SRC, "source range is invalid");
1495 assert!(MIN_DST <= MAX_DST, "target range is invalid");
1496
1497 match ($from_internal::MIN == 0, $internal::MIN == 0) {
1498 (true, true) => {
1500 assert!(
1501 MIN_SRC as u128 >= MIN_DST as u128,
1502 "minimum value cannot be represented in the target range"
1503 );
1504 assert!(
1505 MAX_SRC as u128 <= MAX_DST as u128,
1506 "maximum value cannot be represented in the target range"
1507 );
1508 }
1509 (false, false) => {
1511 assert!(
1512 MIN_SRC as i128 >= MIN_DST as i128,
1513 "minimum value cannot be represented in the target range"
1514 );
1515 assert!(
1516 MAX_SRC as i128 <= MAX_DST as i128,
1517 "maximum value cannot be represented in the target range"
1518 );
1519 }
1520 (true, false) => {
1522 assert!(
1523 MIN_DST < 0 || MIN_SRC as u128 >= MIN_DST as u128,
1524 "minimum value cannot be represented in the target range"
1525 );
1526 assert!(
1527 MAX_DST >= 0
1528 && MAX_SRC as u128 <= i128::MAX as u128
1529 && MAX_SRC as i128 <= MAX_DST as i128,
1530 "maximum value cannot be represented in the target range"
1531 );
1532 }
1533 (false, true) => {
1535 assert!(
1536 MIN_SRC >= 0 && MIN_SRC as u128 >= MIN_DST as u128,
1537 "minimum value cannot be represented in the target range"
1538 );
1539 assert!(
1540 MAX_SRC >= 0 && MAX_SRC as u128 <= MAX_DST as u128,
1541 "maximum value cannot be represented in the target range"
1542 );
1543 }
1544 }
1545 }
1546
1547 unsafe { $type::new_unchecked(value.get() as $internal) }
1549 }
1550 })+
1551
1552 #[cfg(feature = "serde")]
1553 impl<const MIN: $internal, const MAX: $internal> serde_core::Serialize for $type<MIN, MAX> {
1554 #[inline(always)]
1555 fn serialize<S: serde_core::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error>
1556 {
1557 const { assert!(MIN <= MAX); }
1558 self.get().serialize(serializer)
1559 }
1560 }
1561
1562 #[cfg(feature = "serde")]
1563 impl<
1564 const MIN: $internal,
1565 const MAX: $internal,
1566 > serde_core::Serialize for $optional_type<MIN, MAX> {
1567 #[inline(always)]
1568 fn serialize<S: serde_core::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error>
1569 {
1570 const { assert!(MIN <= MAX); }
1571 self.get().serialize(serializer)
1572 }
1573 }
1574
1575 #[cfg(feature = "serde")]
1576 impl<
1577 'de,
1578 const MIN: $internal,
1579 const MAX: $internal,
1580 > serde_core::Deserialize<'de> for $type<MIN, MAX> {
1581 #[inline]
1582 fn deserialize<D: serde_core::Deserializer<'de>>(deserializer: D)
1583 -> Result<Self, D::Error>
1584 {
1585 const { assert!(MIN <= MAX); }
1586 let internal = <$internal>::deserialize(deserializer)?;
1587 Self::new(internal).ok_or_else(||
1588 <D::Error as serde_core::de::Error>::invalid_value(
1589 serde_core::de::Unexpected::Other("integer"),
1590 #[cfg(feature = "alloc")] {
1591 &alloc::format!("an integer in the range {}..={}", MIN, MAX).as_ref()
1592 },
1593 #[cfg(not(feature = "alloc"))] {
1594 &"an integer in the valid range"
1595 }
1596 )
1597 )
1598 }
1599 }
1600
1601 #[cfg(feature = "serde")]
1602 impl<
1603 'de,
1604 const MIN: $internal,
1605 const MAX: $internal,
1606 > serde_core::Deserialize<'de> for $optional_type<MIN, MAX> {
1607 #[inline]
1608 fn deserialize<D: serde_core::Deserializer<'de>>(deserializer: D)
1609 -> Result<Self, D::Error>
1610 {
1611 const { assert!(MIN <= MAX); }
1612 Ok(Self::Some($type::<MIN, MAX>::deserialize(deserializer)?))
1613 }
1614 }
1615
1616 #[cfg(feature = "rand08")]
1617 impl<
1618 const MIN: $internal,
1619 const MAX: $internal,
1620 > rand08::distributions::Distribution<$type<MIN, MAX>> for rand08::distributions::Standard {
1621 #[inline]
1622 fn sample<R: rand08::Rng + ?Sized>(&self, rng: &mut R) -> $type<MIN, MAX> {
1623 const { assert!(MIN <= MAX); }
1624 $type::new(rng.gen_range(MIN..=MAX)).expect("rand failed to generate a valid value")
1625 }
1626 }
1627
1628 if_not_manual_rand_09! {
1629 [$($($skips)+)?]
1630 #[cfg(feature = "rand09")]
1631 impl<
1632 const MIN: $internal,
1633 const MAX: $internal,
1634 > rand09::distr::Distribution<$type<MIN, MAX>> for rand09::distr::StandardUniform {
1635 #[inline]
1636 fn sample<R: rand09::Rng + ?Sized>(&self, rng: &mut R) -> $type<MIN, MAX> {
1637 const { assert!(MIN <= MAX); }
1638 $type::new(rng.random_range(MIN..=MAX)).expect("rand failed to generate a valid value")
1639 }
1640 }
1641 }
1642
1643 if_not_manual_rand_010! {
1644 [$($($skips)+)?]
1645 #[cfg(feature = "rand010")]
1646 impl<
1647 const MIN: $internal,
1648 const MAX: $internal,
1649 > rand010::distr::Distribution<$type<MIN, MAX>> for rand010::distr::StandardUniform {
1650 #[inline]
1651 fn sample<R: rand010::Rng + ?Sized>(&self, rng: &mut R) -> $type<MIN, MAX> {
1652 const { assert!(MIN <= MAX); }
1653 use rand010::RngExt as _;
1654 $type::new(rng.random_range(MIN..=MAX)).expect("rand failed to generate a valid value")
1655 }
1656 }
1657 }
1658
1659 #[cfg(feature = "rand08")]
1660 impl<
1661 const MIN: $internal,
1662 const MAX: $internal,
1663 > rand08::distributions::Distribution<$optional_type<MIN, MAX>>
1664 for rand08::distributions::Standard {
1665 #[inline]
1666 fn sample<R: rand08::Rng + ?Sized>(&self, rng: &mut R) -> $optional_type<MIN, MAX> {
1667 const { assert!(MIN <= MAX); }
1668 rng.r#gen::<Option<$type<MIN, MAX>>>().into()
1669 }
1670 }
1671
1672 #[cfg(feature = "rand09")]
1673 impl<
1674 const MIN: $internal,
1675 const MAX: $internal,
1676 > rand09::distr::Distribution<$optional_type<MIN, MAX>>
1677 for rand09::distr::StandardUniform {
1678 #[inline]
1679 fn sample<R: rand09::Rng + ?Sized>(&self, rng: &mut R) -> $optional_type<MIN, MAX> {
1680 const { assert!(MIN <= MAX); }
1681 if rng.random() {
1682 $optional_type::None
1683 } else {
1684 $optional_type::Some(rng.random::<$type<MIN, MAX>>())
1685 }
1686 }
1687 }
1688
1689 #[cfg(feature = "rand010")]
1690 impl<
1691 const MIN: $internal,
1692 const MAX: $internal,
1693 > rand010::distr::Distribution<$optional_type<MIN, MAX>>
1694 for rand010::distr::StandardUniform {
1695 #[inline]
1696 fn sample<R: rand010::Rng + ?Sized>(&self, rng: &mut R) -> $optional_type<MIN, MAX> {
1697 const { assert!(MIN <= MAX); }
1698 use rand010::RngExt as _;
1699 if rng.random() {
1700 $optional_type::None
1701 } else {
1702 $optional_type::Some(rng.random::<$type<MIN, MAX>>())
1703 }
1704 }
1705 }
1706
1707 #[cfg(feature = "num")]
1708 impl<const MIN: $internal, const MAX: $internal> num_traits::Bounded for $type<MIN, MAX> {
1709 #[inline(always)]
1710 fn min_value() -> Self {
1711 const { assert!(MIN <= MAX); }
1712 Self::MIN
1713 }
1714
1715 #[inline(always)]
1716 fn max_value() -> Self {
1717 const { assert!(MIN <= MAX); }
1718 Self::MAX
1719 }
1720 }
1721
1722 #[cfg(feature = "quickcheck")]
1723 impl<const MIN: $internal, const MAX: $internal> quickcheck::Arbitrary for $type<MIN, MAX> {
1724 #[inline]
1725 fn arbitrary(g: &mut quickcheck::Gen) -> Self {
1726 const { assert!(MIN <= MAX); }
1727 unsafe {
1729 Self::new_unchecked($internal::arbitrary(g).rem_euclid(MAX - MIN + 1) + MIN)
1730 }
1731 }
1732
1733 #[inline]
1734 fn shrink(&self) -> ::alloc::boxed::Box<dyn Iterator<Item = Self>> {
1735 ::alloc::boxed::Box::new(
1736 self.get()
1737 .shrink()
1738 .filter_map(Self::new)
1739 )
1740 }
1741 }
1742
1743 #[cfg(feature = "quickcheck")]
1744 impl<
1745 const MIN: $internal,
1746 const MAX: $internal,
1747 > quickcheck::Arbitrary for $optional_type<MIN, MAX> {
1748 #[inline]
1749 fn arbitrary(g: &mut quickcheck::Gen) -> Self {
1750 const { assert!(MIN <= MAX); }
1751 Option::<$type<MIN, MAX>>::arbitrary(g).into()
1752 }
1753
1754 #[inline]
1755 fn shrink(&self) -> ::alloc::boxed::Box<dyn Iterator<Item = Self>> {
1756 ::alloc::boxed::Box::new(self.get().shrink().map(Self::from))
1757 }
1758 }
1759 )*};
1760}
1761
1762impl_ranged! {
1763 RangedU8 {
1764 mod_name: ranged_u8
1765 alias: ru8
1766 internal: u8
1767 signed: false
1768 unsigned: u8
1769 optional: OptionRangedU8
1770 optional_alias: Option_ru8
1771 from: [
1772 RangedU16(u16)
1773 RangedU32(u32)
1774 RangedU64(u64)
1775 RangedU128(u128)
1776 RangedUsize(usize)
1777 RangedI8(i8)
1778 RangedI16(i16)
1779 RangedI32(i32)
1780 RangedI64(i64)
1781 RangedI128(i128)
1782 RangedIsize(isize)
1783 ]
1784 }
1785 RangedU16 {
1786 mod_name: ranged_u16
1787 alias: ru16
1788 internal: u16
1789 signed: false
1790 unsigned: u16
1791 optional: OptionRangedU16
1792 optional_alias: Option_ru16
1793 from: [
1794 RangedU8(u8)
1795 RangedU32(u32)
1796 RangedU64(u64)
1797 RangedU128(u128)
1798 RangedUsize(usize)
1799 RangedI8(i8)
1800 RangedI16(i16)
1801 RangedI32(i32)
1802 RangedI64(i64)
1803 RangedI128(i128)
1804 RangedIsize(isize)
1805 ]
1806 }
1807 RangedU32 {
1808 mod_name: ranged_u32
1809 alias: ru32
1810 internal: u32
1811 signed: false
1812 unsigned: u32
1813 optional: OptionRangedU32
1814 optional_alias: Option_ru32
1815 from: [
1816 RangedU8(u8)
1817 RangedU16(u16)
1818 RangedU64(u64)
1819 RangedU128(u128)
1820 RangedUsize(usize)
1821 RangedI8(i8)
1822 RangedI16(i16)
1823 RangedI32(i32)
1824 RangedI64(i64)
1825 RangedI128(i128)
1826 RangedIsize(isize)
1827 ]
1828 }
1829 RangedU64 {
1830 mod_name: ranged_u64
1831 alias: ru64
1832 internal: u64
1833 signed: false
1834 unsigned: u64
1835 optional: OptionRangedU64
1836 optional_alias: Option_ru64
1837 from: [
1838 RangedU8(u8)
1839 RangedU16(u16)
1840 RangedU32(u32)
1841 RangedU128(u128)
1842 RangedUsize(usize)
1843 RangedI8(i8)
1844 RangedI16(i16)
1845 RangedI32(i32)
1846 RangedI64(i64)
1847 RangedI128(i128)
1848 RangedIsize(isize)
1849 ]
1850 }
1851 RangedU128 {
1852 mod_name: ranged_u128
1853 alias: ru128
1854 internal: u128
1855 signed: false
1856 unsigned: u128
1857 optional: OptionRangedU128
1858 optional_alias: Option_ru128
1859 from: [
1860 RangedU8(u8)
1861 RangedU16(u16)
1862 RangedU32(u32)
1863 RangedU64(u64)
1864 RangedUsize(usize)
1865 RangedI8(i8)
1866 RangedI16(i16)
1867 RangedI32(i32)
1868 RangedI64(i64)
1869 RangedI128(i128)
1870 RangedIsize(isize)
1871 ]
1872 }
1873 RangedUsize {
1874 mod_name: ranged_usize
1875 alias: rusize
1876 internal: usize
1877 signed: false
1878 unsigned: usize
1879 optional: OptionRangedUsize
1880 optional_alias: Option_rusize
1881 from: [
1882 RangedU8(u8)
1883 RangedU16(u16)
1884 RangedU32(u32)
1885 RangedU64(u64)
1886 RangedU128(u128)
1887 RangedI8(i8)
1888 RangedI16(i16)
1889 RangedI32(i32)
1890 RangedI64(i64)
1891 RangedI128(i128)
1892 RangedIsize(isize)
1893 ]
1894 manual: [rand_09 rand_010]
1895 }
1896 RangedI8 {
1897 mod_name: ranged_i8
1898 alias: ri8
1899 internal: i8
1900 signed: true
1901 unsigned: u8
1902 optional: OptionRangedI8
1903 optional_alias: Option_ri8
1904 from: [
1905 RangedU8(u8)
1906 RangedU16(u16)
1907 RangedU32(u32)
1908 RangedU64(u64)
1909 RangedU128(u128)
1910 RangedUsize(usize)
1911 RangedI16(i16)
1912 RangedI32(i32)
1913 RangedI64(i64)
1914 RangedI128(i128)
1915 RangedIsize(isize)
1916 ]
1917 }
1918 RangedI16 {
1919 mod_name: ranged_i16
1920 alias: ri16
1921 internal: i16
1922 signed: true
1923 unsigned: u16
1924 optional: OptionRangedI16
1925 optional_alias: Option_ri16
1926 from: [
1927 RangedU8(u8)
1928 RangedU16(u16)
1929 RangedU32(u32)
1930 RangedU64(u64)
1931 RangedU128(u128)
1932 RangedUsize(usize)
1933 RangedI8(i8)
1934 RangedI32(i32)
1935 RangedI64(i64)
1936 RangedI128(i128)
1937 RangedIsize(isize)
1938 ]
1939 }
1940 RangedI32 {
1941 mod_name: ranged_i32
1942 alias: ri32
1943 internal: i32
1944 signed: true
1945 unsigned: u32
1946 optional: OptionRangedI32
1947 optional_alias: Option_ri32
1948 from: [
1949 RangedU8(u8)
1950 RangedU16(u16)
1951 RangedU32(u32)
1952 RangedU64(u64)
1953 RangedU128(u128)
1954 RangedUsize(usize)
1955 RangedI8(i8)
1956 RangedI16(i16)
1957 RangedI64(i64)
1958 RangedI128(i128)
1959 RangedIsize(isize)
1960 ]
1961 }
1962 RangedI64 {
1963 mod_name: ranged_i64
1964 alias: ri64
1965 internal: i64
1966 signed: true
1967 unsigned: u64
1968 optional: OptionRangedI64
1969 optional_alias: Option_ri64
1970 from: [
1971 RangedU8(u8)
1972 RangedU16(u16)
1973 RangedU32(u32)
1974 RangedU64(u64)
1975 RangedU128(u128)
1976 RangedUsize(usize)
1977 RangedI8(i8)
1978 RangedI16(i16)
1979 RangedI32(i32)
1980 RangedI128(i128)
1981 RangedIsize(isize)
1982 ]
1983 }
1984 RangedI128 {
1985 mod_name: ranged_i128
1986 alias: ri128
1987 internal: i128
1988 signed: true
1989 unsigned: u128
1990 optional: OptionRangedI128
1991 optional_alias: Option_ri128
1992 from: [
1993 RangedU8(u8)
1994 RangedU16(u16)
1995 RangedU32(u32)
1996 RangedU64(u64)
1997 RangedU128(u128)
1998 RangedUsize(usize)
1999 RangedI8(i8)
2000 RangedI16(i16)
2001 RangedI32(i32)
2002 RangedI64(i64)
2003 RangedIsize(isize)
2004 ]
2005 }
2006 RangedIsize {
2007 mod_name: ranged_isize
2008 alias: risize
2009 internal: isize
2010 signed: true
2011 unsigned: usize
2012 optional: OptionRangedIsize
2013 optional_alias: Option_risize
2014 from: [
2015 RangedU8(u8)
2016 RangedU16(u16)
2017 RangedU32(u32)
2018 RangedU64(u64)
2019 RangedU128(u128)
2020 RangedUsize(usize)
2021 RangedI8(i8)
2022 RangedI16(i16)
2023 RangedI32(i32)
2024 RangedI64(i64)
2025 RangedI128(i128)
2026 ]
2027 manual: [rand_09 rand_010]
2028 }
2029}
2030
2031#[cfg(feature = "rand09")]
2032impl<const MIN: usize, const MAX: usize> rand09::distr::Distribution<RangedUsize<MIN, MAX>>
2033 for rand09::distr::StandardUniform
2034{
2035 #[inline]
2036 fn sample<R: rand09::Rng + ?Sized>(&self, rng: &mut R) -> RangedUsize<MIN, MAX> {
2037 const {
2038 assert!(MIN <= MAX);
2039 }
2040
2041 #[cfg(target_pointer_width = "16")]
2042 let value = rng.random_range(MIN as u16..=MAX as u16) as usize;
2043 #[cfg(target_pointer_width = "32")]
2044 let value = rng.random_range(MIN as u32..=MAX as u32) as usize;
2045 #[cfg(target_pointer_width = "64")]
2046 let value = rng.random_range(MIN as u64..=MAX as u64) as usize;
2047 #[cfg(not(any(
2048 target_pointer_width = "16",
2049 target_pointer_width = "32",
2050 target_pointer_width = "64"
2051 )))]
2052 compile_error("platform has unusual (and unsupported) pointer width");
2053
2054 RangedUsize::new(value).expect("rand failed to generate a valid value")
2055 }
2056}
2057
2058#[cfg(feature = "rand09")]
2059impl<const MIN: isize, const MAX: isize> rand09::distr::Distribution<RangedIsize<MIN, MAX>>
2060 for rand09::distr::StandardUniform
2061{
2062 #[inline]
2063 fn sample<R: rand09::Rng + ?Sized>(&self, rng: &mut R) -> RangedIsize<MIN, MAX> {
2064 const {
2065 assert!(MIN <= MAX);
2066 }
2067
2068 #[cfg(target_pointer_width = "16")]
2069 let value = rng.random_range(MIN as i16..=MAX as i16) as isize;
2070 #[cfg(target_pointer_width = "32")]
2071 let value = rng.random_range(MIN as i32..=MAX as i32) as isize;
2072 #[cfg(target_pointer_width = "64")]
2073 let value = rng.random_range(MIN as i64..=MAX as i64) as isize;
2074 #[cfg(not(any(
2075 target_pointer_width = "16",
2076 target_pointer_width = "32",
2077 target_pointer_width = "64"
2078 )))]
2079 compile_error("platform has unusual (and unsupported) pointer width");
2080
2081 RangedIsize::new(value).expect("rand failed to generate a valid value")
2082 }
2083}
2084
2085#[cfg(feature = "rand010")]
2086impl<const MIN: usize, const MAX: usize> rand010::distr::Distribution<RangedUsize<MIN, MAX>>
2087 for rand010::distr::StandardUniform
2088{
2089 #[inline]
2090 fn sample<R: rand010::Rng + ?Sized>(&self, rng: &mut R) -> RangedUsize<MIN, MAX> {
2091 const {
2092 assert!(MIN <= MAX);
2093 }
2094
2095 use rand010::RngExt as _;
2096
2097 #[cfg(target_pointer_width = "16")]
2098 let value = rng.random_range(MIN as u16..=MAX as u16) as usize;
2099 #[cfg(target_pointer_width = "32")]
2100 let value = rng.random_range(MIN as u32..=MAX as u32) as usize;
2101 #[cfg(target_pointer_width = "64")]
2102 let value = rng.random_range(MIN as u64..=MAX as u64) as usize;
2103 #[cfg(not(any(
2104 target_pointer_width = "16",
2105 target_pointer_width = "32",
2106 target_pointer_width = "64"
2107 )))]
2108 compile_error("platform has unusual (and unsupported) pointer width");
2109
2110 RangedUsize::new(value).expect("rand failed to generate a valid value")
2111 }
2112}
2113
2114#[cfg(feature = "rand010")]
2115impl<const MIN: isize, const MAX: isize> rand010::distr::Distribution<RangedIsize<MIN, MAX>>
2116 for rand010::distr::StandardUniform
2117{
2118 #[inline]
2119 fn sample<R: rand010::Rng + ?Sized>(&self, rng: &mut R) -> RangedIsize<MIN, MAX> {
2120 const {
2121 assert!(MIN <= MAX);
2122 }
2123
2124 use rand010::RngExt as _;
2125
2126 #[cfg(target_pointer_width = "16")]
2127 let value = rng.random_range(MIN as i16..=MAX as i16) as isize;
2128 #[cfg(target_pointer_width = "32")]
2129 let value = rng.random_range(MIN as i32..=MAX as i32) as isize;
2130 #[cfg(target_pointer_width = "64")]
2131 let value = rng.random_range(MIN as i64..=MAX as i64) as isize;
2132 #[cfg(not(any(
2133 target_pointer_width = "16",
2134 target_pointer_width = "32",
2135 target_pointer_width = "64"
2136 )))]
2137 compile_error("platform has unusual (and unsupported) pointer width");
2138
2139 RangedIsize::new(value).expect("rand failed to generate a valid value")
2140 }
2141}