1#![no_std]
2
3extern crate alloc;
4extern crate num_traits;
5
6use num_traits::{One, Zero};
7use core::cmp;
8use core::ops::{Add, Sub};
9
10mod id;
11mod id_list;
12mod id_range;
13mod id_vector;
14
15pub use id::Id;
16pub use id_list::{IdFreeList, NoneAsNullId, NullId};
17pub use id_range::{IdRange, ReverseIdRange};
18pub use id_vector::{IdSlice, IdVec, MutIdSlice};
19
20pub trait FromUsize {
21 fn from_usize(idx: usize) -> Self;
22}
23
24pub trait ToUsize {
25 fn to_usize(&self) -> usize;
26}
27
28pub trait IntegerHandle:
29 Copy
30 + Clone
31 + Add<Output = Self>
32 + Sub<Output = Self>
33 + cmp::Ord
34 + PartialEq
35 + PartialOrd
36 + FromUsize
37 + ToUsize
38 + Zero
39 + One
40{
41}
42
43pub trait Identifier: Copy + FromUsize + ToUsize + PartialEq {
44 type Handle: IntegerHandle;
45 type Tag;
46}
47
48impl Identifier for u8 {
49 type Handle = u8;
50 type Tag = ();
51}
52impl Identifier for u16 {
53 type Handle = u16;
54 type Tag = ();
55}
56impl Identifier for u32 {
57 type Handle = u32;
58 type Tag = ();
59}
60impl Identifier for u64 {
61 type Handle = u64;
62 type Tag = ();
63}
64impl Identifier for i8 {
65 type Handle = i8;
66 type Tag = ();
67}
68impl Identifier for i16 {
69 type Handle = i16;
70 type Tag = ();
71}
72impl Identifier for i32 {
73 type Handle = i32;
74 type Tag = ();
75}
76impl Identifier for i64 {
77 type Handle = i64;
78 type Tag = ();
79}
80
81impl ToUsize for u8 {
82 #[inline]
83 fn to_usize(&self) -> usize {
84 *self as usize
85 }
86}
87impl ToUsize for u16 {
88 #[inline]
89 fn to_usize(&self) -> usize {
90 *self as usize
91 }
92}
93impl ToUsize for u32 {
94 #[inline]
95 fn to_usize(&self) -> usize {
96 *self as usize
97 }
98}
99impl ToUsize for u64 {
100 #[inline]
101 fn to_usize(&self) -> usize {
102 *self as usize
103 }
104}
105impl ToUsize for usize {
106 #[inline]
107 fn to_usize(&self) -> usize {
108 *self
109 }
110}
111impl ToUsize for i8 {
112 #[inline]
113 fn to_usize(&self) -> usize {
114 debug_assert!(*self >= 0);
115 *self as usize
116 }
117}
118impl ToUsize for i16 {
119 #[inline]
120 fn to_usize(&self) -> usize {
121 debug_assert!(*self >= 0);
122 *self as usize
123 }
124}
125impl ToUsize for i32 {
126 #[inline]
127 fn to_usize(&self) -> usize {
128 debug_assert!(*self >= 0);
129 *self as usize
130 }
131}
132impl ToUsize for i64 {
133 #[inline]
134 fn to_usize(&self) -> usize {
135 debug_assert!(*self >= 0);
136 *self as usize
137 }
138}
139impl ToUsize for isize {
140 #[inline]
141 fn to_usize(&self) -> usize {
142 debug_assert!(*self >= 0);
143 *self as usize
144 }
145}
146
147impl FromUsize for u8 {
148 #[inline]
149 fn from_usize(idx: usize) -> u8 {
150 idx as u8
151 }
152}
153impl FromUsize for u16 {
154 #[inline]
155 fn from_usize(idx: usize) -> u16 {
156 idx as u16
157 }
158}
159impl FromUsize for u32 {
160 #[inline]
161 fn from_usize(idx: usize) -> u32 {
162 idx as u32
163 }
164}
165impl FromUsize for u64 {
166 #[inline]
167 fn from_usize(idx: usize) -> u64 {
168 idx as u64
169 }
170}
171impl FromUsize for usize {
172 #[inline]
173 fn from_usize(idx: usize) -> usize {
174 idx
175 }
176}
177impl FromUsize for i8 {
178 #[inline]
179 fn from_usize(idx: usize) -> i8 {
180 idx as i8
181 }
182}
183impl FromUsize for i16 {
184 #[inline]
185 fn from_usize(idx: usize) -> i16 {
186 idx as i16
187 }
188}
189impl FromUsize for i32 {
190 #[inline]
191 fn from_usize(idx: usize) -> i32 {
192 idx as i32
193 }
194}
195impl FromUsize for i64 {
196 #[inline]
197 fn from_usize(idx: usize) -> i64 {
198 idx as i64
199 }
200}
201impl FromUsize for isize {
202 #[inline]
203 fn from_usize(idx: usize) -> isize {
204 idx as isize
205 }
206}
207
208impl IntegerHandle for u8 {}
209impl IntegerHandle for u16 {}
210impl IntegerHandle for u32 {}
211impl IntegerHandle for u64 {}
212impl IntegerHandle for usize {}
213impl IntegerHandle for i8 {}
214impl IntegerHandle for i16 {}
215impl IntegerHandle for i32 {}
216impl IntegerHandle for i64 {}
217impl IntegerHandle for isize {}
218
219#[test]
279fn test_copy_id() {
280 #[derive(Debug)]
281 struct Foo;
282
283 let a: Id<Foo, u32> = Id::new(0);
285 let b = a;
286 let c = a;
287 assert_eq!(b, c);
288
289 let r1: IdRange<Foo, u32> = IdRange::new(0..10);
291
292 let r2 = r1;
293 let r3 = r1;
294 assert_eq!(r2, r3);
295}
296
297#[test]
298fn test_reverese_id_range() {
299 fn range(first: u16, count: u16) -> IdRange<u16, u16> {
300 IdRange::new(first..(first + count))
301 }
302 let mut iter = ReverseIdRange::new(range(1, 5));
303 assert_eq!(iter.next(), Some(Id::new(5)));
304 assert_eq!(iter.next(), Some(Id::new(4)));
305 assert_eq!(iter.next(), Some(Id::new(3)));
306 assert_eq!(iter.next(), Some(Id::new(2)));
307 assert_eq!(iter.next(), Some(Id::new(1)));
308 assert_eq!(iter.next(), None);
309 assert_eq!(iter.next(), None);
310}