1use std::{cmp::Ordering, fmt, hash, marker::PhantomData, num::NonZeroU32, ops};
2
3type Index = NonZeroU32;
7
8use crate::Span;
9use indexmap::set::IndexSet;
10
11#[derive(Clone, Copy, Debug, thiserror::Error, PartialEq)]
12#[error("Handle {index} of {kind} is either not present, or inaccessible yet")]
13pub struct BadHandle {
14 pub kind: &'static str,
15 pub index: usize,
16}
17
18impl BadHandle {
19 fn new<T>(handle: Handle<T>) -> Self {
20 Self {
21 kind: std::any::type_name::<T>(),
22 index: handle.index(),
23 }
24 }
25}
26
27#[cfg_attr(feature = "serialize", derive(serde::Serialize))]
31#[cfg_attr(feature = "deserialize", derive(serde::Deserialize))]
32#[cfg_attr(
33 any(feature = "serialize", feature = "deserialize"),
34 serde(transparent)
35)]
36#[cfg_attr(feature = "arbitrary", derive(arbitrary::Arbitrary))]
37pub struct Handle<T> {
38 index: Index,
39 #[cfg_attr(any(feature = "serialize", feature = "deserialize"), serde(skip))]
40 marker: PhantomData<T>,
41}
42
43impl<T> Clone for Handle<T> {
44 fn clone(&self) -> Self {
45 Handle {
46 index: self.index,
47 marker: self.marker,
48 }
49 }
50}
51
52impl<T> Copy for Handle<T> {}
53
54impl<T> PartialEq for Handle<T> {
55 fn eq(&self, other: &Self) -> bool {
56 self.index == other.index
57 }
58}
59
60impl<T> Eq for Handle<T> {}
61
62impl<T> PartialOrd for Handle<T> {
63 fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
64 self.index.partial_cmp(&other.index)
65 }
66}
67
68impl<T> Ord for Handle<T> {
69 fn cmp(&self, other: &Self) -> Ordering {
70 self.index.cmp(&other.index)
71 }
72}
73
74impl<T> fmt::Debug for Handle<T> {
75 fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
76 write!(formatter, "[{}]", self.index)
77 }
78}
79
80impl<T> hash::Hash for Handle<T> {
81 fn hash<H: hash::Hasher>(&self, hasher: &mut H) {
82 self.index.hash(hasher)
83 }
84}
85
86impl<T> Handle<T> {
87 #[cfg(test)]
88 pub const DUMMY: Self = Handle {
89 index: unsafe { NonZeroU32::new_unchecked(u32::MAX) },
90 marker: PhantomData,
91 };
92
93 pub(crate) const fn new(index: Index) -> Self {
94 Handle {
95 index,
96 marker: PhantomData,
97 }
98 }
99
100 pub const fn index(self) -> usize {
102 let index = self.index.get() - 1;
103 index as usize
104 }
105
106 fn from_usize(index: usize) -> Self {
108 let handle_index = u32::try_from(index + 1)
109 .ok()
110 .and_then(Index::new)
111 .expect("Failed to insert into arena. Handle overflows");
112 Handle::new(handle_index)
113 }
114
115 const unsafe fn from_usize_unchecked(index: usize) -> Self {
117 Handle::new(Index::new_unchecked((index + 1) as u32))
118 }
119}
120
121#[cfg_attr(feature = "serialize", derive(serde::Serialize))]
123#[cfg_attr(feature = "deserialize", derive(serde::Deserialize))]
124#[cfg_attr(
125 any(feature = "serialize", feature = "deserialize"),
126 serde(transparent)
127)]
128#[cfg_attr(feature = "arbitrary", derive(arbitrary::Arbitrary))]
129pub struct Range<T> {
130 inner: ops::Range<u32>,
131 #[cfg_attr(any(feature = "serialize", feature = "deserialize"), serde(skip))]
132 marker: PhantomData<T>,
133}
134
135impl<T> Range<T> {
136 pub(crate) const fn erase_type(self) -> Range<()> {
137 let Self { inner, marker: _ } = self;
138 Range {
139 inner,
140 marker: PhantomData,
141 }
142 }
143}
144
145#[derive(Clone, Debug, thiserror::Error)]
147#[error("Handle range {range:?} of {kind} is either not present, or inaccessible yet")]
148pub struct BadRangeError {
149 kind: &'static str,
152 range: Range<()>,
153}
154
155impl BadRangeError {
156 pub fn new<T>(range: Range<T>) -> Self {
157 Self {
158 kind: std::any::type_name::<T>(),
159 range: range.erase_type(),
160 }
161 }
162}
163
164impl<T> Clone for Range<T> {
165 fn clone(&self) -> Self {
166 Range {
167 inner: self.inner.clone(),
168 marker: self.marker,
169 }
170 }
171}
172
173impl<T> fmt::Debug for Range<T> {
174 fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
175 write!(formatter, "[{}..{}]", self.inner.start + 1, self.inner.end)
176 }
177}
178
179impl<T> Iterator for Range<T> {
180 type Item = Handle<T>;
181 fn next(&mut self) -> Option<Self::Item> {
182 if self.inner.start < self.inner.end {
183 self.inner.start += 1;
184 Some(Handle {
185 index: NonZeroU32::new(self.inner.start).unwrap(),
186 marker: self.marker,
187 })
188 } else {
189 None
190 }
191 }
192}
193
194impl<T> Range<T> {
195 pub fn new_from_bounds(first: Handle<T>, last: Handle<T>) -> Self {
196 Self {
197 inner: (first.index() as u32)..(last.index() as u32 + 1),
198 marker: Default::default(),
199 }
200 }
201}
202
203#[cfg_attr(feature = "clone", derive(Clone))]
210#[cfg_attr(feature = "serialize", derive(serde::Serialize))]
211#[cfg_attr(feature = "serialize", serde(transparent))]
212#[cfg_attr(feature = "arbitrary", derive(arbitrary::Arbitrary))]
213#[cfg_attr(test, derive(PartialEq))]
214pub struct Arena<T> {
215 data: Vec<T>,
217 #[cfg(feature = "span")]
218 #[cfg_attr(feature = "serialize", serde(skip))]
219 span_info: Vec<Span>,
220}
221
222impl<T> Default for Arena<T> {
223 fn default() -> Self {
224 Self::new()
225 }
226}
227
228impl<T: fmt::Debug> fmt::Debug for Arena<T> {
229 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
230 f.debug_map().entries(self.iter()).finish()
231 }
232}
233
234impl<T> Arena<T> {
235 pub const fn new() -> Self {
237 Arena {
238 data: Vec::new(),
239 #[cfg(feature = "span")]
240 span_info: Vec::new(),
241 }
242 }
243
244 #[allow(clippy::missing_const_for_fn)] pub fn into_inner(self) -> Vec<T> {
247 self.data
248 }
249
250 pub fn len(&self) -> usize {
252 self.data.len()
253 }
254
255 pub fn is_empty(&self) -> bool {
257 self.data.is_empty()
258 }
259
260 pub fn iter(&self) -> impl DoubleEndedIterator<Item = (Handle<T>, &T)> {
263 self.data
264 .iter()
265 .enumerate()
266 .map(|(i, v)| unsafe { (Handle::from_usize_unchecked(i), v) })
267 }
268
269 pub fn iter_mut(&mut self) -> impl DoubleEndedIterator<Item = (Handle<T>, &mut T)> {
272 self.data
273 .iter_mut()
274 .enumerate()
275 .map(|(i, v)| unsafe { (Handle::from_usize_unchecked(i), v) })
276 }
277
278 pub fn append(&mut self, value: T, span: Span) -> Handle<T> {
280 #[cfg(not(feature = "span"))]
281 let _ = span;
282 let index = self.data.len();
283 self.data.push(value);
284 #[cfg(feature = "span")]
285 self.span_info.push(span);
286 Handle::from_usize(index)
287 }
288
289 pub fn fetch_if<F: Fn(&T) -> bool>(&self, fun: F) -> Option<Handle<T>> {
291 self.data
292 .iter()
293 .position(fun)
294 .map(|index| unsafe { Handle::from_usize_unchecked(index) })
295 }
296
297 pub fn fetch_if_or_append<F: Fn(&T, &T) -> bool>(
302 &mut self,
303 value: T,
304 span: Span,
305 fun: F,
306 ) -> Handle<T> {
307 if let Some(index) = self.data.iter().position(|d| fun(d, &value)) {
308 unsafe { Handle::from_usize_unchecked(index) }
309 } else {
310 self.append(value, span)
311 }
312 }
313
314 pub fn fetch_or_append(&mut self, value: T, span: Span) -> Handle<T>
316 where
317 T: PartialEq,
318 {
319 self.fetch_if_or_append(value, span, T::eq)
320 }
321
322 pub fn try_get(&self, handle: Handle<T>) -> Result<&T, BadHandle> {
323 self.data
324 .get(handle.index())
325 .ok_or_else(|| BadHandle::new(handle))
326 }
327
328 pub fn get_mut(&mut self, handle: Handle<T>) -> &mut T {
330 self.data.get_mut(handle.index()).unwrap()
331 }
332
333 pub fn range_from(&self, old_length: usize) -> Range<T> {
335 Range {
336 inner: old_length as u32..self.data.len() as u32,
337 marker: PhantomData,
338 }
339 }
340
341 pub fn clear(&mut self) {
343 self.data.clear()
344 }
345
346 pub fn get_span(&self, handle: Handle<T>) -> Span {
347 #[cfg(feature = "span")]
348 {
349 *self
350 .span_info
351 .get(handle.index())
352 .unwrap_or(&Span::default())
353 }
354 #[cfg(not(feature = "span"))]
355 {
356 let _ = handle;
357 Span::default()
358 }
359 }
360
361 pub fn check_contains_handle(&self, handle: Handle<T>) -> Result<(), BadHandle> {
363 if handle.index() < self.data.len() {
364 Ok(())
365 } else {
366 Err(BadHandle::new(handle))
367 }
368 }
369
370 pub fn check_contains_range(&self, range: &Range<T>) -> Result<(), BadRangeError> {
372 if range.inner.start > range.inner.end
376 || self
377 .check_contains_handle(Handle::new(range.inner.end.try_into().unwrap()))
378 .is_err()
379 {
380 Err(BadRangeError::new(range.clone()))
381 } else {
382 Ok(())
383 }
384 }
385}
386
387#[cfg(feature = "deserialize")]
388impl<'de, T> serde::Deserialize<'de> for Arena<T>
389where
390 T: serde::Deserialize<'de>,
391{
392 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
393 where
394 D: serde::Deserializer<'de>,
395 {
396 let data = Vec::deserialize(deserializer)?;
397 #[cfg(feature = "span")]
398 let span_info = std::iter::repeat(Span::default())
399 .take(data.len())
400 .collect();
401
402 Ok(Self {
403 data,
404 #[cfg(feature = "span")]
405 span_info,
406 })
407 }
408}
409
410impl<T> ops::Index<Handle<T>> for Arena<T> {
411 type Output = T;
412 fn index(&self, handle: Handle<T>) -> &T {
413 &self.data[handle.index()]
414 }
415}
416
417impl<T> ops::IndexMut<Handle<T>> for Arena<T> {
418 fn index_mut(&mut self, handle: Handle<T>) -> &mut T {
419 &mut self.data[handle.index()]
420 }
421}
422
423impl<T> ops::Index<Range<T>> for Arena<T> {
424 type Output = [T];
425 fn index(&self, range: Range<T>) -> &[T] {
426 &self.data[range.inner.start as usize..range.inner.end as usize]
427 }
428}
429
430#[cfg(test)]
431mod tests {
432 use super::*;
433
434 #[test]
435 fn append_non_unique() {
436 let mut arena: Arena<u8> = Arena::new();
437 let t1 = arena.append(0, Default::default());
438 let t2 = arena.append(0, Default::default());
439 assert!(t1 != t2);
440 assert!(arena[t1] == arena[t2]);
441 }
442
443 #[test]
444 fn append_unique() {
445 let mut arena: Arena<u8> = Arena::new();
446 let t1 = arena.append(0, Default::default());
447 let t2 = arena.append(1, Default::default());
448 assert!(t1 != t2);
449 assert!(arena[t1] != arena[t2]);
450 }
451
452 #[test]
453 fn fetch_or_append_non_unique() {
454 let mut arena: Arena<u8> = Arena::new();
455 let t1 = arena.fetch_or_append(0, Default::default());
456 let t2 = arena.fetch_or_append(0, Default::default());
457 assert!(t1 == t2);
458 assert!(arena[t1] == arena[t2])
459 }
460
461 #[test]
462 fn fetch_or_append_unique() {
463 let mut arena: Arena<u8> = Arena::new();
464 let t1 = arena.fetch_or_append(0, Default::default());
465 let t2 = arena.fetch_or_append(1, Default::default());
466 assert!(t1 != t2);
467 assert!(arena[t1] != arena[t2]);
468 }
469}
470
471#[cfg_attr(feature = "clone", derive(Clone))]
486pub struct UniqueArena<T> {
487 set: IndexSet<T>,
488
489 #[cfg(feature = "span")]
496 span_info: Vec<Span>,
497}
498
499impl<T> UniqueArena<T> {
500 pub fn new() -> Self {
502 UniqueArena {
503 set: IndexSet::new(),
504 #[cfg(feature = "span")]
505 span_info: Vec::new(),
506 }
507 }
508
509 pub fn len(&self) -> usize {
511 self.set.len()
512 }
513
514 pub fn is_empty(&self) -> bool {
516 self.set.is_empty()
517 }
518
519 pub fn clear(&mut self) {
521 self.set.clear();
522 #[cfg(feature = "span")]
523 self.span_info.clear();
524 }
525
526 pub fn get_span(&self, handle: Handle<T>) -> Span {
534 #[cfg(feature = "span")]
535 {
536 *self
537 .span_info
538 .get(handle.index())
539 .unwrap_or(&Span::default())
540 }
541 #[cfg(not(feature = "span"))]
542 {
543 let _ = handle;
544 Span::default()
545 }
546 }
547}
548
549impl<T: Eq + hash::Hash> UniqueArena<T> {
550 pub fn iter(&self) -> impl DoubleEndedIterator<Item = (Handle<T>, &T)> {
553 self.set.iter().enumerate().map(|(i, v)| {
554 let position = i + 1;
555 let index = unsafe { Index::new_unchecked(position as u32) };
556 (Handle::new(index), v)
557 })
558 }
559
560 pub fn insert(&mut self, value: T, span: Span) -> Handle<T> {
575 let (index, added) = self.set.insert_full(value);
576
577 #[cfg(feature = "span")]
578 {
579 if added {
580 debug_assert!(index == self.span_info.len());
581 self.span_info.push(span);
582 }
583
584 debug_assert!(self.set.len() == self.span_info.len());
585 }
586
587 #[cfg(not(feature = "span"))]
588 let _ = (span, added);
589
590 Handle::from_usize(index)
591 }
592
593 pub fn replace(&mut self, old: Handle<T>, new: T) {
600 let (index, added) = self.set.insert_full(new);
601 assert!(added && index == self.set.len() - 1);
602
603 self.set.swap_remove_index(old.index()).unwrap();
604 }
605
606 pub fn get(&self, value: &T) -> Option<Handle<T>> {
611 self.set
612 .get_index_of(value)
613 .map(|index| unsafe { Handle::from_usize_unchecked(index) })
614 }
615
616 pub fn get_handle(&self, handle: Handle<T>) -> Result<&T, BadHandle> {
618 self.set
619 .get_index(handle.index())
620 .ok_or_else(|| BadHandle::new(handle))
621 }
622
623 pub fn check_contains_handle(&self, handle: Handle<T>) -> Result<(), BadHandle> {
625 if handle.index() < self.set.len() {
626 Ok(())
627 } else {
628 Err(BadHandle::new(handle))
629 }
630 }
631}
632
633impl<T> Default for UniqueArena<T> {
634 fn default() -> Self {
635 Self::new()
636 }
637}
638
639impl<T: fmt::Debug + Eq + hash::Hash> fmt::Debug for UniqueArena<T> {
640 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
641 f.debug_map().entries(self.iter()).finish()
642 }
643}
644
645impl<T> ops::Index<Handle<T>> for UniqueArena<T> {
646 type Output = T;
647 fn index(&self, handle: Handle<T>) -> &T {
648 &self.set[handle.index()]
649 }
650}
651
652#[cfg(feature = "serialize")]
653impl<T> serde::Serialize for UniqueArena<T>
654where
655 T: Eq + hash::Hash + serde::Serialize,
656{
657 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
658 where
659 S: serde::Serializer,
660 {
661 self.set.serialize(serializer)
662 }
663}
664
665#[cfg(feature = "deserialize")]
666impl<'de, T> serde::Deserialize<'de> for UniqueArena<T>
667where
668 T: Eq + hash::Hash + serde::Deserialize<'de>,
669{
670 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
671 where
672 D: serde::Deserializer<'de>,
673 {
674 let set = IndexSet::deserialize(deserializer)?;
675 #[cfg(feature = "span")]
676 let span_info = std::iter::repeat(Span::default()).take(set.len()).collect();
677
678 Ok(Self {
679 set,
680 #[cfg(feature = "span")]
681 span_info,
682 })
683 }
684}
685
686#[cfg(feature = "arbitrary")]
688impl<'a, T> arbitrary::Arbitrary<'a> for UniqueArena<T>
689where
690 T: Eq + hash::Hash + arbitrary::Arbitrary<'a>,
691{
692 fn arbitrary(u: &mut arbitrary::Unstructured<'a>) -> arbitrary::Result<Self> {
693 let mut arena = Self::default();
694 for elem in u.arbitrary_iter()? {
695 arena.set.insert(elem?);
696 #[cfg(feature = "span")]
697 arena.span_info.push(Span::UNDEFINED);
698 }
699 Ok(arena)
700 }
701
702 fn arbitrary_take_rest(u: arbitrary::Unstructured<'a>) -> arbitrary::Result<Self> {
703 let mut arena = Self::default();
704 for elem in u.arbitrary_take_rest_iter()? {
705 arena.set.insert(elem?);
706 #[cfg(feature = "span")]
707 arena.span_info.push(Span::UNDEFINED);
708 }
709 Ok(arena)
710 }
711
712 #[inline]
713 fn size_hint(depth: usize) -> (usize, Option<usize>) {
714 let depth_hint = <usize as arbitrary::Arbitrary>::size_hint(depth);
715 arbitrary::size_hint::and(depth_hint, (0, None))
716 }
717}