1use num_traits::{One, PrimInt, Zero};
10use std::cmp::Ordering;
11use std::fmt;
12use std::fmt::Formatter;
13use std::hash::{Hash, Hasher};
14use std::marker::PhantomData;
15
16#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
19pub struct Index<T, Int = u32> {
20 index: Int,
21 phantom: PhantomData<T>,
22}
23
24impl<T, Int> fmt::Debug for Index<T, Int>
25where
26 Int: std::fmt::Display,
27{
28 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
29 write!(f, "Index({})", self.index)
30 }
31}
32
33impl<T, Int: Hash> Hash for Index<T, Int> {
34 fn hash<H: Hasher>(&self, state: &mut H) {
35 self.index.hash(state)
36 }
37}
38
39impl<T, Int: Copy> Copy for Index<T, Int> {}
40
41impl<T, Int: Copy> Clone for Index<T, Int> {
42 fn clone(&self) -> Self {
43 *self
44 }
45}
46
47impl<T, Int: PartialEq> Eq for Index<T, Int> {}
48
49impl<T, Int: PartialEq> PartialEq for Index<T, Int> {
50 fn eq(&self, other: &Self) -> bool {
51 self.index.eq(&other.index)
52 }
53}
54
55impl<T, Int: PartialOrd + Ord> Ord for Index<T, Int> {
56 fn cmp(&self, other: &Self) -> Ordering {
57 self.index.cmp(&other.index)
58 }
59}
60
61impl<T, Int: PartialOrd> PartialOrd for Index<T, Int> {
62 fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
63 self.index.partial_cmp(&other.index)
64 }
65}
66
67impl<T, Int: fmt::Display> fmt::Display for Index<T, Int> {
68 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
69 write!(f, "{}", self.index)
70 }
71}
72
73impl<T, Int: Copy> Index<T, Int> {
74 pub(crate) fn new(index: Int) -> Self {
75 Index {
76 index,
77 phantom: Default::default(),
78 }
79 }
80
81 pub fn value(&self) -> Int {
83 self.index
84 }
85}
86
87#[derive(Debug, Clone)]
89#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
90pub(crate) struct IndexGenerator<T, Int = u32> {
91 counter: Int,
92 phantom: PhantomData<T>,
93}
94
95impl<T, Int: PrimInt + Zero + One> Default for IndexGenerator<T, Int> {
96 fn default() -> Self {
97 Self::new(Int::zero())
98 }
99}
100
101impl<T, Int: PrimInt + One> IndexGenerator<T, Int> {
102 pub fn new(start: Int) -> Self {
104 IndexGenerator {
105 counter: start,
106 phantom: Default::default(),
107 }
108 }
109
110 pub fn next(&mut self) -> Index<T, Int> {
120 let index = Index::new(self.counter);
121 self.counter = self.counter + Int::one();
122 index
123 }
124}