count_enum/lib.rs
1//! 操作值域有限的类型
2//!
3//! 它给值域一个顺序,序号和迭代之类都按照这个顺序。
4//!
5//! [`Enum`] 提供了基础的方法,可使用 [`GenericEnum`] 自动实现。
6//! 使用 [`iter_each`] 或 [`iter_each_from`] 迭代 [`Enum`] 的值域。
7
8#![no_std]
9
10mod generic;
11mod impls;
12mod iter;
13
14use core::num::NonZeroUsize;
15pub use generic::GenericEnum;
16pub use iter::{iter_each, iter_each_from, IterEachFrom};
17
18/// 枚举
19///
20/// 建议使用 [`GenericEnum`] 自动实现。
21pub trait Enum: Clone {
22 /// 类型的取值的总数
23 ///
24 /// 如果溢出,则为 `None`。
25 ///
26 /// ```
27 /// # use count_enum::Enum;
28 /// assert_eq!(Option::<bool>::CARD, Some(3));
29 /// assert_eq!(i128::CARD, None);
30 /// ```
31 const CARD: Option<usize>;
32
33 /// 值的序号
34 ///
35 /// 返回值应小于 `CARD`(如果有)。如果溢出,则返回 `None`。
36 ///
37 /// ```
38 /// # use count_enum::Enum;
39 /// assert_eq!(Some(true).to_index(), Some(2));
40 /// assert_eq!(12i8.to_index(), Some(140));
41 /// assert_eq!(0u128.to_index(), Some(0));
42 /// assert_eq!(u128::MAX.to_index(), None);
43 /// ```
44 fn to_index(&self) -> Option<usize>;
45
46 /// 序号对应的值
47 ///
48 /// 输入应小于 `CARD`(如果有),否则返回 `None`。
49 ///
50 /// ```
51 /// # use count_enum::Enum;
52 /// assert_eq!(Option::<bool>::from_index(2), Some(Some(true)));
53 /// assert_eq!(i8::from_index(0), Some(-128));
54 /// assert_eq!(i16::from_index(99999), None);
55 /// ```
56 fn from_index(i: usize) -> Option<Self>;
57
58 /// 第一个值
59 ///
60 /// 如果值域为空,则返回 `None`。
61 ///
62 /// ```
63 /// # use count_enum::Enum;
64 /// assert_eq!(i8::first(), Some(-128));
65 /// ```
66 fn first() -> Option<Self>;
67
68 /// 最后一个值
69 ///
70 /// 如果值域为空,则返回 `None`。
71 ///
72 /// ```
73 /// # use count_enum::Enum;
74 /// assert_eq!(i8::last(), Some(127));
75 /// ```
76 fn last() -> Option<Self>;
77
78 /// 上一个值
79 ///
80 /// 如果已经是第一个值,则返回 `None`。
81 ///
82 /// ```
83 /// # use count_enum::Enum;
84 /// assert_eq!(0i8.prev(), Some(-1));
85 /// ```
86 fn prev(&self) -> Option<Self>;
87
88 /// 下一个值
89 ///
90 /// 如果已经是最后一个值,则返回 `None`。
91 ///
92 /// ```
93 /// # use count_enum::Enum;
94 /// assert_eq!(0i8.succ(), Some(1));
95 /// ```
96 fn succ(&self) -> Option<Self>;
97
98 /// 此后的值的总数
99 ///
100 /// 总数包含此值,因此非零。如果溢出,则返回 `None`。
101 ///
102 /// ```
103 /// # use count_enum::Enum;
104 /// assert_eq!(bool::count_from(&false), Some(2.try_into().unwrap()));
105 /// ```
106 fn count_from(from: &Self) -> Option<NonZeroUsize>;
107
108 /// 遍历每一个值
109 ///
110 /// 相当于 `iter_each().fold(init, f)`。
111 fn fold_each<B, F>(init: B, f: F) -> B
112 where
113 F: FnMut(B, Self) -> B;
114
115 /// 从某个值开始遍历每一个值
116 ///
117 /// 相当于 `iter_each_from(from).fold(init, f)`。
118 fn fold_each_from<B, F>(from: &Self, init: B, f: F) -> B
119 where
120 F: FnMut(B, Self) -> B;
121}