Skip to main content

pui_arena/base/
sparse.rs

1//! Sparse Arenas - Fast Access, Slow Iteration, Fast Mutation, Small memory footprint
2//!
3//! A sparse arena has a minimal footprint, it stores a linked-list of empty
4//! slots embeded in the same location as the values, so as long as the size
5//! of you values is greater than or equal to `usize`, then there is no memory
6//! overhead. This linked-list of empty slots means that insertion and deletion
7//! are `O(1)` operations.
8//!
9//! Each slot is versioned by using [`Version`] trait. See [`Version`] for docs
10//! on version exhaustion. Once a slot's version exhausts, it will not be pushed
11//! onto the linked list. This prevents it from ever being used again.
12
13use core::{
14    marker::PhantomData,
15    mem::{replace, ManuallyDrop},
16    ops::{Index, IndexMut},
17};
18
19use pui_vec::PuiVec;
20
21use crate::{
22    version::{DefaultVersion, Version},
23    ArenaKey, BuildArenaKey,
24};
25
26union Data<T> {
27    value: ManuallyDrop<T>,
28    next: usize,
29}
30
31struct Slot<T, V: Version> {
32    version: V,
33    data: Data<T>,
34}
35
36/// A sparse arena
37#[derive(Debug, Clone)]
38pub struct Arena<T, I = (), V: Version = DefaultVersion> {
39    slots: PuiVec<Slot<T, V>, I>,
40    next: usize,
41    num_elements: usize,
42}
43
44/// An empty slot in a sparse arena
45pub struct VacantEntry<'a, T, I, V: Version = DefaultVersion> {
46    arena: &'a mut Arena<T, I, V>,
47    new_next: usize,
48}
49
50impl<T, V: Version> Drop for Slot<T, V> {
51    fn drop(&mut self) {
52        if self.version.is_full() {
53            unsafe { ManuallyDrop::drop(&mut self.data.value) }
54        }
55    }
56}
57
58impl<T, V: Version> Slot<T, V> {
59    unsafe fn remove_unchecked(&mut self, index: usize, next: &mut usize) -> T {
60        let value = ManuallyDrop::take(&mut self.data.value);
61        match self.version.mark_empty() {
62            Ok(next_version) => {
63                self.version = next_version;
64
65                self.data = Data {
66                    next: replace(next, index),
67                };
68            }
69            Err(next_version) => self.version = next_version,
70        }
71
72        value
73    }
74
75    unsafe fn delete_unchecked(&mut self, index: usize, next: &mut usize) {
76        struct Fixup<'a, T, V: Version>(&'a mut Slot<T, V>, usize, &'a mut usize);
77
78        impl<T, V: Version> Drop for Fixup<'_, T, V> {
79            fn drop(&mut self) {
80                let Self(ref mut slot, index, ref mut next) = *self;
81                match unsafe { slot.version.mark_empty() } {
82                    Err(next_version) => slot.version = next_version,
83                    Ok(next_version) => {
84                        slot.version = next_version;
85
86                        slot.data = Data {
87                            next: replace(next, index),
88                        };
89                    }
90                }
91            }
92        }
93
94        let fixup = Fixup(self, index, next);
95
96        ManuallyDrop::drop(&mut fixup.0.data.value);
97    }
98}
99
100impl<T> Default for Arena<T> {
101    fn default() -> Self { Self::new() }
102}
103
104impl<T> Arena<T> {
105    /// Create a new arena
106    pub const fn new() -> Self { Self::INIT }
107}
108
109impl<T, V: Version> Arena<T, (), V> {
110    /// An empty arena
111    pub const INIT: Self = Self {
112        slots: PuiVec::new(()),
113        next: 0,
114        num_elements: 0,
115    };
116
117    /// Clear the arena without reducing it's capacity
118    pub fn clear(&mut self) {
119        self.next = 0;
120        self.slots.vec_mut().clear();
121    }
122}
123
124impl<T, I, V: Version> VacantEntry<'_, T, I, V> {
125    /// Get the key associated with the `VacantEntry`, this key can be used
126    /// once this `VacantEntry` gets filled
127    pub fn key<K: BuildArenaKey<I, V>>(&self) -> K {
128        unsafe {
129            K::new_unchecked(
130                self.arena.next,
131                self.arena
132                    .slots
133                    .get_unchecked(self.arena.next)
134                    .version
135                    .mark_full()
136                    .save(),
137                self.arena.ident(),
138            )
139        }
140    }
141
142    /// Insert an element into the vacant entry
143    pub fn insert<K: BuildArenaKey<I, V>>(self, value: T) -> K {
144        let slot = unsafe { self.arena.slots.get_unchecked_mut(self.arena.next) };
145        slot.data = Data {
146            value: ManuallyDrop::new(value),
147        };
148        slot.version = unsafe { slot.version.mark_full() };
149        let version = unsafe { slot.version.save() };
150        let index = self.arena.next;
151        self.arena.next = self.new_next;
152        self.arena.num_elements += 1;
153
154        unsafe { K::new_unchecked(index, version, self.arena.ident()) }
155    }
156}
157
158impl<T, I, V: Version> Arena<T, I, V> {
159    /// Create a new arena with the given identifier
160    pub fn with_ident(ident: I) -> Self {
161        Self {
162            slots: PuiVec::new(ident),
163            next: 0,
164            num_elements: 0,
165        }
166    }
167
168    /// Get the associated identifier for this arena
169    pub fn ident(&self) -> &I { self.slots.ident() }
170
171    /// Returns true if the arena is empty
172    pub fn is_empty(&self) -> bool { self.num_elements == 0 }
173
174    /// Returns the number of elements in this arena
175    pub fn len(&self) -> usize { self.num_elements }
176
177    /// Returns the capacity of this arena
178    pub fn capacity(&self) -> usize { self.slots.capacity() }
179
180    /// Reserves capacity for at least additional more elements to be inserted
181    /// in the given collection. The collection may reserve more space to avoid
182    /// frequent reallocations. After calling reserve, capacity will be greater
183    /// than or equal to `self.len() + additional`. Does nothing if capacity is
184    /// already sufficient.
185    pub fn reserve(&mut self, additional: usize) {
186        if let Some(additional) = self.capacity().wrapping_sub(self.num_elements).checked_sub(additional) {
187            self.slots.reserve(additional)
188        }
189    }
190
191    /// Reserves the minimum capacity for exactly additional more elements
192    /// to be inserted in the given collection. After calling reserve_exact,
193    /// capacity will be greater than or equal to `self.len() + additional`.
194    /// Does nothing if the capacity is already sufficient.
195    ///
196    /// Note that the allocator may give the collection more space than it
197    /// requests. Therefore, capacity can not be relied upon to be precisely
198    /// minimal. Prefer reserve if future insertions are expected.
199    pub fn reserve_exact(&mut self, additional: usize) {
200        if let Some(additional) = self.capacity().wrapping_sub(self.num_elements).checked_sub(additional) {
201            self.slots.reserve_exact(additional)
202        }
203    }
204
205    /// Check if an index is in bounds, and if it is return a `Key<_, _>` to it
206    #[inline]
207    pub fn parse_key<K: BuildArenaKey<I, V>>(&self, index: usize) -> Option<K> {
208        let slot = self.slots.get(index)?;
209        if slot.version.is_full() {
210            Some(unsafe { K::new_unchecked(index, slot.version.save(), self.slots.ident()) })
211        } else {
212            None
213        }
214    }
215
216    /// Return a handle to a vacant entry allowing for further manipulation.
217    ///
218    /// This function is useful when creating values that must contain their
219    /// key. The returned VacantEntry reserves a slot in the arena and is able
220    /// to query the associated key.
221    pub fn vacant_entry(&mut self) -> VacantEntry<'_, T, I, V> {
222        #[cold]
223        #[inline(never)]
224        pub fn allocate_vacant_slot<T, I, V: Version>(this: &mut Arena<T, I, V>) {
225            this.next = this.slots.len();
226            let _: usize = this.slots.push(Slot {
227                version: V::EMPTY,
228                data: Data {
229                    next: this.next.wrapping_add(1),
230                },
231            });
232        }
233
234        if self.slots.len() == self.next {
235            allocate_vacant_slot(self);
236        }
237
238        let slot = unsafe { self.slots.get_unchecked_mut(self.next) };
239
240        VacantEntry {
241            new_next: unsafe { slot.data.next },
242            arena: self,
243        }
244    }
245
246    /// Insert a value in the arena, returning key assigned to the value.
247    ///
248    /// The returned key can later be used to retrieve or remove the value
249    /// using indexed lookup and remove. Additional capacity is allocated
250    /// if needed.
251    pub fn insert<K: BuildArenaKey<I, V>>(&mut self, value: T) -> K { self.vacant_entry().insert(value) }
252
253    /// Return true if a value is associated with the given key.
254    pub fn contains<K: ArenaKey<I, V>>(&self, key: K) -> bool {
255        let is_index_guarnateed_valid = key.validate_ident(self.ident(), crate::Validator::new()).into_inner();
256        let index = key.index();
257        if !is_index_guarnateed_valid && self.slots.len() <= index {
258            return false
259        }
260        let version = unsafe { self.slots.get_unchecked(index).version };
261
262        match key.version() {
263            Some(saved) => version.equals_saved(saved),
264            None => version.is_full(),
265        }
266    }
267
268    /// Remove and return the value associated with the given key.
269    ///
270    /// The key is then released and may be associated with future stored values,
271    /// if the versioning strategy allows it.
272    ///
273    /// Panics if key is not associated with a value.
274    #[track_caller]
275    pub fn remove<K: ArenaKey<I, V>>(&mut self, key: K) -> T {
276        self.try_remove(key)
277            .expect("Could not remove from an `Arena` using a stale `Key`")
278    }
279
280    /// Remove and return the value associated with the given key.
281    ///
282    /// The key is then released and may be associated with future stored values,
283    /// if the versioning strategy allows it.
284    ///
285    /// Returns `None` if key is not associated with a value.
286    pub fn try_remove<K: ArenaKey<I, V>>(&mut self, key: K) -> Option<T> {
287        if self.contains(&key) {
288            let index = key.index();
289            Some(unsafe { self.remove_unchecked(index) })
290        } else {
291            None
292        }
293    }
294
295    unsafe fn remove_unchecked(&mut self, index: usize) -> T {
296        self.num_elements -= 1;
297        self.slots
298            .get_unchecked_mut(index)
299            .remove_unchecked(index, &mut self.next)
300    }
301
302    /// Removes the value associated with the given key.
303    ///
304    /// The key is then released and may be associated with future stored values,
305    /// if the versioning strategy allows it.
306    ///
307    /// Returns true if the value was removed, an false otherwise
308    pub fn delete<K: ArenaKey<I, V>>(&mut self, key: K) -> bool {
309        if self.contains(&key) {
310            unsafe {
311                self.delete_unchecked(key.index());
312                true
313            }
314        } else {
315            false
316        }
317    }
318
319    pub(crate) unsafe fn delete_unchecked(&mut self, index: usize) {
320        self.num_elements -= 1;
321        self.slots
322            .get_unchecked_mut(index)
323            .delete_unchecked(index, &mut self.next)
324    }
325
326    /// Return a shared reference to the value associated with the given key.
327    ///
328    /// If the given key is not associated with a value, then None is returned.
329    pub fn get<K: ArenaKey<I, V>>(&self, key: K) -> Option<&T> {
330        if self.contains(&key) {
331            unsafe { Some(self.get_unchecked(key.index())) }
332        } else {
333            None
334        }
335    }
336
337    /// Return a unique reference to the value associated with the given key.
338    ///
339    /// If the given key is not associated with a value, then None is returned.
340    pub fn get_mut<K: ArenaKey<I, V>>(&mut self, key: K) -> Option<&mut T> {
341        if self.contains(&key) {
342            unsafe { Some(self.get_unchecked_mut(key.index())) }
343        } else {
344            None
345        }
346    }
347
348    /// Return a shared reference to the value associated with the
349    /// given key without performing bounds checking, or checks
350    /// if there is a value associated to the key
351    ///
352    /// # Safety
353    ///
354    /// `contains` should return true with the given index.
355    pub unsafe fn get_unchecked(&self, index: usize) -> &T { &*self.slots.get_unchecked(index).data.value }
356
357    /// Return a unique reference to the value associated with the
358    /// given key without performing bounds checking, or checks
359    /// if there is a value associated to the key
360    ///
361    /// # Safety
362    ///
363    /// `contains` should return true with the given index.
364    pub unsafe fn get_unchecked_mut(&mut self, index: usize) -> &mut T {
365        &mut *self.slots.get_unchecked_mut(index).data.value
366    }
367
368    /// Deletes all elements from the arena
369    pub fn delete_all(&mut self) { self.retain(|_| false) }
370
371    /// Retain only the elements specified by the predicate.
372    ///
373    /// If the predicate returns for a given element true,
374    /// then the element is kept in the arena.
375    pub fn retain<F: FnMut(&mut T) -> bool>(&mut self, mut f: F) {
376        for i in 0..self.slots.len() {
377            if let Some(value) = self.get_mut(unsafe { crate::TrustedIndex::new(i) }) {
378                if !f(value) {
379                    unsafe {
380                        self.slots.get_unchecked_mut(i).delete_unchecked(i, &mut self.next);
381                    }
382                }
383            }
384        }
385    }
386
387    /// An iterator over the keys of the arena, in no particular order
388    pub fn keys<K: BuildArenaKey<I, V>>(&self) -> Keys<'_, T, I, V, K> {
389        Keys {
390            entries: self.entries(),
391        }
392    }
393
394    /// An iterator of shared references to values of the arena,
395    /// in no particular order
396    pub fn iter(&self) -> Iter<'_, T, V> {
397        Iter {
398            slots: Occupied {
399                slots: self.slots.iter(),
400            },
401        }
402    }
403
404    /// An iterator of unique references to values of the arena,
405    /// in no particular order
406    pub fn iter_mut(&mut self) -> IterMut<'_, T, V> {
407        IterMut {
408            slots: Occupied {
409                slots: self.slots.iter_mut(),
410            },
411        }
412    }
413
414    /// Return a draining iterator that removes all elements from the
415    /// arena and yields the removed items.
416    ///
417    /// Note: Elements are removed even if the iterator is only partially
418    /// consumed or not consumed at all.
419    pub fn drain(&mut self) -> Drain<'_, T, V> {
420        Drain {
421            slots: Occupied {
422                slots: self.slots.iter_mut().enumerate(),
423            },
424            next: &mut self.next,
425            num_elements: &mut self.num_elements,
426        }
427    }
428
429    /// Return a draining iterator that removes all elements specified by the predicate
430    /// from the arena and yields the removed items.
431    ///
432    /// If the predicate returns true for a given element, then it is removed from
433    /// the arena, and yielded from the iterator.
434    ///
435    /// Note: Elements are removed even if the iterator is only partially
436    /// consumed or not consumed at all.
437    pub fn drain_filter<F: FnMut(&mut T) -> bool>(&mut self, filter: F) -> DrainFilter<'_, T, V, F> {
438        DrainFilter {
439            slots: Occupied {
440                slots: self.slots.iter_mut().enumerate(),
441            },
442            next: &mut self.next,
443            num_elements: &mut self.num_elements,
444            filter,
445            panicked: false,
446        }
447    }
448
449    /// An iterator of keys and shared references to values of the arena,
450    /// in no particular order, with each key being associated
451    /// to the corrosponding value
452    pub fn entries<K: BuildArenaKey<I, V>>(&self) -> Entries<'_, T, I, V, K> {
453        let ident = self.ident();
454
455        Entries {
456            slots: Occupied {
457                slots: self.slots.iter().enumerate(),
458            },
459            ident,
460            key: PhantomData,
461        }
462    }
463
464    /// An iterator of keys and unique references to values of the arena,
465    /// in no particular order, with each key being associated
466    /// to the corrosponding value
467    pub fn entries_mut<K: BuildArenaKey<I, V>>(&mut self) -> EntriesMut<'_, T, I, V, K> {
468        let (ident, slots) = self.slots.as_mut_parts();
469
470        EntriesMut {
471            slots: Occupied {
472                slots: slots.iter_mut().enumerate(),
473            },
474            ident,
475            key: PhantomData,
476        }
477    }
478
479    /// An iterator of keys and values of the arena,
480    /// in no particular order, with each key being associated
481    /// to the corrosponding value
482    pub fn into_entries<K: BuildArenaKey<I, V>>(self) -> IntoEntries<T, I, V, K> {
483        let (ident, slots) = unsafe { self.slots.into_raw_parts() };
484
485        IntoEntries {
486            slots: Occupied {
487                slots: slots.into_iter().enumerate(),
488            },
489            ident,
490            key: PhantomData,
491        }
492    }
493}
494
495impl<T, I, V: Version> IntoIterator for Arena<T, I, V> {
496    type Item = T;
497    type IntoIter = IntoIter<T, V>;
498
499    fn into_iter(self) -> Self::IntoIter {
500        IntoIter {
501            slots: Occupied {
502                slots: unsafe { self.slots.into_raw_parts().1.into_iter() },
503            },
504        }
505    }
506}
507
508impl<T, I, V: Version, K: ArenaKey<I, V>> Index<K> for Arena<T, I, V> {
509    type Output = T;
510
511    #[track_caller]
512    fn index(&self, key: K) -> &Self::Output { self.get(key).expect("Tried to access `Arena` with a stale `Key`") }
513}
514
515impl<T, I, V: Version, K: ArenaKey<I, V>> IndexMut<K> for Arena<T, I, V> {
516    #[track_caller]
517    fn index_mut(&mut self, key: K) -> &mut Self::Output {
518        self.get_mut(key).expect("Tried to access `Arena` with a stale `Key`")
519    }
520}
521
522impl<T, I, V: Version> Extend<T> for Arena<T, I, V> {
523    #[allow(clippy::drop_copy)]
524    fn extend<Iter: IntoIterator<Item = T>>(&mut self, iter: Iter) {
525        let iter = iter.into_iter();
526        self.reserve(iter.size_hint().0);
527        iter.for_each(move |value| drop::<usize>(self.vacant_entry().insert(value)));
528    }
529}
530
531use core::fmt;
532
533impl<T: Clone, V: Version> Clone for Slot<T, V> {
534    fn clone(&self) -> Self {
535        Self {
536            version: self.version,
537            data: if self.version.is_full() {
538                Data {
539                    value: unsafe { self.data.value.clone() },
540                }
541            } else {
542                Data {
543                    next: unsafe { self.data.next },
544                }
545            },
546        }
547    }
548
549    fn clone_from(&mut self, source: &Self) {
550        if self.version.is_full() && source.version.is_full() {
551            self.version = source.version;
552            unsafe {
553                self.data.value.clone_from(&source.data.value);
554            }
555        } else {
556            *self = source.clone()
557        }
558    }
559}
560
561impl<T: fmt::Debug, V: Version + fmt::Debug> fmt::Debug for Slot<T, V> {
562    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
563        if self.version.is_full() {
564            f.debug_struct("Occupied")
565                .field("version", &self.version)
566                .field("value", unsafe { &*self.data.value })
567                .finish()
568        } else {
569            f.debug_struct("Vacant")
570                .field("version", &self.version)
571                .field("next", unsafe { &self.data.next })
572                .finish()
573        }
574    }
575}
576
577struct Occupied<I> {
578    slots: I,
579}
580
581trait AsSlot {
582    type Item;
583    type Version: Version;
584
585    fn as_slot(&self) -> &Slot<Self::Item, Self::Version>;
586}
587
588impl<T, V: Version> AsSlot for Slot<T, V> {
589    type Item = T;
590    type Version = V;
591
592    #[inline]
593    fn as_slot(&self) -> &Slot<Self::Item, Self::Version> { self }
594}
595
596impl<T, V: Version> AsSlot for &mut Slot<T, V> {
597    type Item = T;
598    type Version = V;
599
600    #[inline]
601    fn as_slot(&self) -> &Slot<Self::Item, Self::Version> { self }
602}
603
604impl<T, V: Version> AsSlot for &Slot<T, V> {
605    type Item = T;
606    type Version = V;
607
608    #[inline]
609    fn as_slot(&self) -> &Slot<Self::Item, Self::Version> { self }
610}
611
612impl<T: AsSlot> AsSlot for (usize, T) {
613    type Item = T::Item;
614    type Version = T::Version;
615
616    #[inline]
617    fn as_slot(&self) -> &Slot<Self::Item, Self::Version> { self.1.as_slot() }
618}
619
620impl<I: Iterator> Iterator for Occupied<I>
621where
622    I::Item: AsSlot,
623{
624    type Item = I::Item;
625
626    fn next(&mut self) -> Option<Self::Item> { self.slots.by_ref().find(|slot| slot.as_slot().version.is_full()) }
627}
628
629impl<I: DoubleEndedIterator> DoubleEndedIterator for Occupied<I>
630where
631    I::Item: AsSlot,
632{
633    fn next_back(&mut self) -> Option<Self::Item> { self.slots.by_ref().rfind(|slot| slot.as_slot().version.is_full()) }
634}
635
636/// Returned by [`Arena::keys`]
637pub struct Keys<'a, T, I, V: Version, K> {
638    entries: Entries<'a, T, I, V, K>,
639}
640
641impl<'a, T, I, V: Version, K: BuildArenaKey<I, V>> Iterator for Keys<'a, T, I, V, K> {
642    type Item = K;
643
644    fn next(&mut self) -> Option<Self::Item> { self.entries.next().map(|(key, _)| key) }
645}
646
647impl<'a, T, I, V: Version, K: BuildArenaKey<I, V>> DoubleEndedIterator for Keys<'a, T, I, V, K> {
648    fn next_back(&mut self) -> Option<Self::Item> { self.entries.next_back().map(|(key, _)| key) }
649}
650
651/// Returned by [`Arena::iter`]
652pub struct Iter<'a, T, V: Version> {
653    slots: Occupied<core::slice::Iter<'a, Slot<T, V>>>,
654}
655
656impl<'a, T, V: Version> Iterator for Iter<'a, T, V> {
657    type Item = &'a T;
658
659    fn next(&mut self) -> Option<Self::Item> { self.slots.next().map(|slot| unsafe { &*slot.data.value }) }
660}
661
662impl<T, V: Version> DoubleEndedIterator for Iter<'_, T, V> {
663    fn next_back(&mut self) -> Option<Self::Item> { self.slots.next_back().map(|slot| unsafe { &*slot.data.value }) }
664}
665
666/// Returned by [`Arena::iter_mut`]
667pub struct IterMut<'a, T, V: Version> {
668    slots: Occupied<core::slice::IterMut<'a, Slot<T, V>>>,
669}
670
671impl<'a, T, V: Version> Iterator for IterMut<'a, T, V> {
672    type Item = &'a mut T;
673
674    fn next(&mut self) -> Option<Self::Item> { self.slots.next().map(|slot| unsafe { &mut *slot.data.value }) }
675}
676
677impl<T, V: Version> DoubleEndedIterator for IterMut<'_, T, V> {
678    fn next_back(&mut self) -> Option<Self::Item> {
679        self.slots.next_back().map(|slot| unsafe { &mut *slot.data.value })
680    }
681}
682
683/// Returned by [`Arena::into_iter`]
684pub struct IntoIter<T, V: Version> {
685    slots: Occupied<std::vec::IntoIter<Slot<T, V>>>,
686}
687
688impl<T, V: Version> Iterator for IntoIter<T, V> {
689    type Item = T;
690
691    fn next(&mut self) -> Option<Self::Item> {
692        self.slots.next().map(|slot| unsafe {
693            let mut slot = ManuallyDrop::new(slot);
694            ManuallyDrop::take(&mut slot.data.value)
695        })
696    }
697}
698
699impl<T, V: Version> DoubleEndedIterator for IntoIter<T, V> {
700    fn next_back(&mut self) -> Option<Self::Item> {
701        self.slots.next_back().map(|slot| unsafe {
702            let mut slot = ManuallyDrop::new(slot);
703            ManuallyDrop::take(&mut slot.data.value)
704        })
705    }
706}
707
708/// Returned by [`Arena::drain`]
709pub struct Drain<'a, T, V: Version> {
710    slots: Occupied<core::iter::Enumerate<core::slice::IterMut<'a, Slot<T, V>>>>,
711    next: &'a mut usize,
712    num_elements: &'a mut usize,
713}
714
715impl<T, V: Version> Drop for Drain<'_, T, V> {
716    fn drop(&mut self) { self.for_each(drop); }
717}
718
719impl<'a, T, V: Version> Iterator for Drain<'a, T, V> {
720    type Item = T;
721
722    fn next(&mut self) -> Option<Self::Item> {
723        let next = &mut *self.next;
724        let num_elements = &mut *self.num_elements;
725        self.slots.next().map(|(index, slot)| unsafe {
726            *num_elements -= 1;
727            slot.remove_unchecked(index, next)
728        })
729    }
730}
731
732impl<T, V: Version> DoubleEndedIterator for Drain<'_, T, V> {
733    fn next_back(&mut self) -> Option<Self::Item> {
734        let next = &mut *self.next;
735        let num_elements = &mut *self.num_elements;
736        self.slots.next_back().map(|(index, slot)| unsafe {
737            *num_elements -= 1;
738            slot.remove_unchecked(index, next)
739        })
740    }
741}
742
743/// Returned by [`Arena::drain_filter`]
744pub struct DrainFilter<'a, T, V: Version, F: FnMut(&mut T) -> bool> {
745    slots: Occupied<core::iter::Enumerate<core::slice::IterMut<'a, Slot<T, V>>>>,
746    next: &'a mut usize,
747    num_elements: &'a mut usize,
748    filter: F,
749    panicked: bool,
750}
751
752impl<T, V: Version, F: FnMut(&mut T) -> bool> Drop for DrainFilter<'_, T, V, F> {
753    fn drop(&mut self) {
754        if !self.panicked {
755            self.for_each(drop);
756        }
757    }
758}
759
760impl<'a, T, V: Version, F: FnMut(&mut T) -> bool> Iterator for DrainFilter<'a, T, V, F> {
761    type Item = T;
762
763    fn next(&mut self) -> Option<Self::Item> {
764        let filter = &mut self.filter;
765        let panicked = &mut self.panicked;
766        let (index, slot) = self
767            .slots
768            .try_fold((), |(), (index, slot)| {
769                let panicked = crate::SetOnDrop(panicked);
770                let return_value = filter(unsafe { &mut *slot.data.value });
771                panicked.defuse();
772                if return_value {
773                    Err((index, slot))
774                } else {
775                    Ok(())
776                }
777            })
778            .err()?;
779        *self.num_elements -= 1;
780        Some(unsafe { slot.remove_unchecked(index, self.next) })
781    }
782}
783
784impl<T, V: Version, F: FnMut(&mut T) -> bool> DoubleEndedIterator for DrainFilter<'_, T, V, F> {
785    fn next_back(&mut self) -> Option<Self::Item> {
786        let filter = &mut self.filter;
787        let (index, slot) = self
788            .slots
789            .try_rfold((), |(), (index, slot)| {
790                if filter(unsafe { &mut *slot.data.value }) {
791                    Err((index, slot))
792                } else {
793                    Ok(())
794                }
795            })
796            .err()?;
797        *self.num_elements -= 1;
798        Some(unsafe { slot.remove_unchecked(index, self.next) })
799    }
800}
801
802/// Returned by [`Arena::entries`]
803pub struct Entries<'a, T, I, V: Version, K> {
804    slots: Occupied<core::iter::Enumerate<core::slice::Iter<'a, Slot<T, V>>>>,
805    ident: &'a I,
806    key: PhantomData<fn() -> K>,
807}
808
809impl<'a, T, I, V: Version, K: BuildArenaKey<I, V>> Iterator for Entries<'a, T, I, V, K> {
810    type Item = (K, &'a T);
811
812    fn next(&mut self) -> Option<Self::Item> {
813        let ident = self.ident;
814        self.slots
815            .next()
816            .map(|(index, slot)| unsafe { (K::new_unchecked(index, slot.version.save(), ident), &*slot.data.value) })
817    }
818}
819
820impl<T, I, V: Version, K: BuildArenaKey<I, V>> DoubleEndedIterator for Entries<'_, T, I, V, K> {
821    fn next_back(&mut self) -> Option<Self::Item> {
822        let ident = self.ident;
823        self.slots
824            .next_back()
825            .map(|(index, slot)| unsafe { (K::new_unchecked(index, slot.version.save(), ident), &*slot.data.value) })
826    }
827}
828
829/// Returned by [`Arena::entries_mut`]
830pub struct EntriesMut<'a, T, I, V: Version, K> {
831    slots: Occupied<core::iter::Enumerate<core::slice::IterMut<'a, Slot<T, V>>>>,
832    ident: &'a I,
833    key: PhantomData<fn() -> K>,
834}
835
836impl<'a, T, I, V: Version, K: BuildArenaKey<I, V>> Iterator for EntriesMut<'a, T, I, V, K> {
837    type Item = (K, &'a mut T);
838
839    fn next(&mut self) -> Option<Self::Item> {
840        let ident = self.ident;
841        self.slots.next().map(|(index, slot)| unsafe {
842            (
843                K::new_unchecked(index, slot.version.save(), ident),
844                &mut *slot.data.value,
845            )
846        })
847    }
848}
849
850impl<T, I, V: Version, K: BuildArenaKey<I, V>> DoubleEndedIterator for EntriesMut<'_, T, I, V, K> {
851    fn next_back(&mut self) -> Option<Self::Item> {
852        let ident = self.ident;
853        self.slots.next_back().map(|(index, slot)| unsafe {
854            (
855                K::new_unchecked(index, slot.version.save(), ident),
856                &mut *slot.data.value,
857            )
858        })
859    }
860}
861
862/// Returned by [`Arena::into_entries`]
863pub struct IntoEntries<T, I, V: Version, K> {
864    slots: Occupied<core::iter::Enumerate<std::vec::IntoIter<Slot<T, V>>>>,
865    ident: I,
866    key: PhantomData<fn() -> K>,
867}
868
869impl<'a, T, I, V: Version, K: BuildArenaKey<I, V>> Iterator for IntoEntries<T, I, V, K> {
870    type Item = (K, T);
871
872    fn next(&mut self) -> Option<Self::Item> {
873        let ident = &self.ident;
874        self.slots.next().map(|(index, slot)| unsafe {
875            let mut slot = ManuallyDrop::new(slot);
876            let value = ManuallyDrop::take(&mut slot.data.value);
877            (K::new_unchecked(index, slot.version.save(), ident), value)
878        })
879    }
880}
881
882impl<T, I, V: Version, K: BuildArenaKey<I, V>> DoubleEndedIterator for IntoEntries<T, I, V, K> {
883    fn next_back(&mut self) -> Option<Self::Item> {
884        let ident = &self.ident;
885        self.slots.next_back().map(|(index, slot)| unsafe {
886            let mut slot = ManuallyDrop::new(slot);
887            let value = ManuallyDrop::take(&mut slot.data.value);
888            (K::new_unchecked(index, slot.version.save(), ident), value)
889        })
890    }
891}
892
893#[cfg(test)]
894mod test {
895    use super::*;
896    use std::vec::Vec;
897
898    #[test]
899    fn basic() {
900        let mut arena = Arena::new();
901
902        let a: usize = arena.insert(0);
903        assert_eq!(a, 0);
904        assert_eq!(arena[a], 0);
905        assert_eq!(arena.remove(a), 0);
906        assert_eq!(arena.get(a), None);
907
908        let b: usize = arena.insert(10);
909        assert_eq!(b, 0);
910        assert_eq!(arena[b], 10);
911
912        let b: usize = arena.insert(20);
913        assert_eq!(b, 1);
914        assert_eq!(arena[b], 20);
915        assert_eq!(arena.remove(a), 10);
916        assert_eq!(arena.get(a), None);
917
918        let c: usize = arena.insert(30);
919        assert_eq!(c, 0);
920        assert_eq!(arena[c], 30);
921        assert_eq!(arena.remove(b), 20);
922        assert_eq!(arena.get(b), None);
923        assert_eq!(arena.remove(c), 30);
924        assert_eq!(arena.get(c), None);
925    }
926
927    #[test]
928    fn basic_reinsertion() {
929        let mut arena = Arena::new();
930        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
931        for i in (0..ins_values.len()).rev().step_by(3) {
932            let key = ins_values.remove(i);
933            arena.remove(key);
934        }
935        for i in ins_values.len()..10 {
936            ins_values.push(arena.insert(i * 100));
937        }
938    }
939
940    #[test]
941    #[allow(clippy::many_single_char_names)]
942    fn zero_sized() {
943        let mut arena = Arena::new();
944
945        let a: usize = arena.insert(());
946        let b: usize = arena.insert(());
947        let c: usize = arena.insert(());
948        let d: usize = arena.insert(());
949        let e: usize = arena.insert(());
950
951        arena.remove(b);
952        arena.remove(d);
953        arena.remove(a);
954        arena.remove(c);
955        arena.remove(e);
956
957        let a: usize = arena.insert(());
958        let b: usize = arena.insert(());
959        let c: usize = arena.insert(());
960        let d: usize = arena.insert(());
961        let e: usize = arena.insert(());
962
963        arena.remove(b);
964        arena.remove(d);
965        arena.remove(a);
966        arena.remove(c);
967        arena.remove(e);
968    }
969
970    #[test]
971    fn basic_retain() {
972        let mut arena = Arena::new();
973        for i in 0..10 {
974            let _: usize = arena.insert(i);
975        }
976        arena.retain(|&mut i| i % 3 == 0);
977        let mut items = arena.iter().copied().collect::<Vec<_>>();
978        items.sort_unstable();
979        assert_eq!(items, [0, 3, 6, 9]);
980    }
981
982    #[test]
983    fn iter_keys_insert_only() {
984        let mut arena = Arena::new();
985        let ins_keys = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
986        let mut iter_keys = arena.keys().collect::<Vec<usize>>();
987        iter_keys.sort_unstable();
988        assert_eq!(ins_keys, iter_keys);
989    }
990
991    #[test]
992    fn iter_keys_rev_insert_only() {
993        let mut arena = Arena::new();
994        let ins_keys = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
995        let mut iter_keys = arena.keys().rev().collect::<Vec<usize>>();
996        iter_keys.sort_unstable();
997
998        assert_eq!(ins_keys, iter_keys);
999    }
1000
1001    #[test]
1002    fn iter_keys_with_removal() {
1003        let mut arena = Arena::new();
1004        let mut ins_keys = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1005        for i in (0..ins_keys.len()).rev().step_by(3) {
1006            let key = ins_keys.remove(i);
1007            arena.remove(key);
1008        }
1009        let mut iter_keys = arena.keys().collect::<Vec<usize>>();
1010        iter_keys.sort_unstable();
1011        assert_eq!(ins_keys, iter_keys);
1012    }
1013
1014    #[test]
1015    fn iter_keys_rev_with_removal() {
1016        let mut arena = Arena::new();
1017        let mut ins_keys = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1018        for i in (0..ins_keys.len()).rev().step_by(3) {
1019            let key = ins_keys.remove(i);
1020            arena.remove(key);
1021        }
1022        ins_keys.sort_unstable();
1023        let mut iter_keys = arena.keys().rev().collect::<Vec<usize>>();
1024        iter_keys.sort_unstable();
1025        assert_eq!(ins_keys, iter_keys);
1026    }
1027
1028    #[test]
1029    fn iter_keys_with_reinsertion() {
1030        let mut arena = Arena::new();
1031        let mut ins_keys = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1032        for i in (0..ins_keys.len()).rev().step_by(3) {
1033            let key = ins_keys.remove(i);
1034            arena.remove(key);
1035        }
1036        for i in ins_keys.len()..10 {
1037            ins_keys.push(arena.insert(i * 100));
1038        }
1039        let mut iter_keys = arena.keys().collect::<Vec<usize>>();
1040        let mut rev_iter_keys = arena.keys().rev().collect::<Vec<usize>>();
1041
1042        // the order that the keys come out doesn't matter,
1043        // so put them in a canonical order
1044        ins_keys.sort_unstable();
1045        iter_keys.sort_unstable();
1046        rev_iter_keys.sort_unstable();
1047
1048        assert_eq!(ins_keys, iter_keys);
1049        assert_eq!(ins_keys, rev_iter_keys);
1050    }
1051
1052    #[test]
1053    fn iter_values_insert_only() {
1054        let mut arena = Arena::new();
1055        let _ = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1056        let mut iter_values = arena.iter().copied().collect::<Vec<_>>();
1057        iter_values.sort_unstable();
1058        assert_eq!(iter_values, [0, 10, 20, 30, 40, 50, 60, 70, 80, 90]);
1059    }
1060
1061    #[test]
1062    fn iter_values_rev_insert_only() {
1063        let mut arena = Arena::new();
1064        let _ = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1065        let mut iter_values = arena.iter().copied().rev().collect::<Vec<_>>();
1066        iter_values.sort_unstable();
1067        assert_eq!(iter_values, [0, 10, 20, 30, 40, 50, 60, 70, 80, 90]);
1068    }
1069
1070    #[test]
1071    fn iter_values_with_removal() {
1072        let mut arena = Arena::new();
1073        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1074        for i in (0..ins_values.len()).rev().step_by(3) {
1075            let key = ins_values.remove(i);
1076            arena.remove(key);
1077        }
1078        let mut iter_values = arena.iter().copied().collect::<Vec<_>>();
1079        iter_values.sort_unstable();
1080        assert_eq!(iter_values, [10, 20, 40, 50, 70, 80]);
1081    }
1082
1083    #[test]
1084    fn iter_values_rev_with_removal() {
1085        let mut arena = Arena::new();
1086        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1087        for i in (0..ins_values.len()).rev().step_by(3) {
1088            let key = ins_values.remove(i);
1089            arena.remove(key);
1090        }
1091        let mut iter_values = arena.iter().copied().rev().collect::<Vec<_>>();
1092        iter_values.sort_unstable();
1093        assert_eq!(iter_values, [10, 20, 40, 50, 70, 80]);
1094    }
1095
1096    #[test]
1097    fn iter_values_with_reinsertion() {
1098        let mut arena = Arena::new();
1099        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1100        for i in (0..ins_values.len()).rev().step_by(3) {
1101            let key = ins_values.remove(i);
1102            arena.remove(key);
1103        }
1104        for i in ins_values.len()..10 {
1105            ins_values.push(arena.insert(i * 100));
1106        }
1107        let mut iter_values = arena.iter().copied().collect::<Vec<usize>>();
1108        let mut rev_iter_values = arena.iter().copied().rev().collect::<Vec<usize>>();
1109
1110        // the order that the iter come out doesn't matter,
1111        // so put them in a canonical order
1112        iter_values.sort_unstable();
1113        rev_iter_values.sort_unstable();
1114
1115        assert_eq!(iter_values, [10, 20, 40, 50, 70, 80, 600, 700, 800, 900]);
1116        assert_eq!(rev_iter_values, [10, 20, 40, 50, 70, 80, 600, 700, 800, 900]);
1117    }
1118
1119    #[test]
1120    fn iter_values_mut_insert_only() {
1121        let mut arena = Arena::new();
1122        let _ = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1123        let mut iter_values_mut = arena.iter_mut().map(|&mut x| x).collect::<Vec<_>>();
1124        iter_values_mut.sort_unstable();
1125        assert_eq!(iter_values_mut, [0, 10, 20, 30, 40, 50, 60, 70, 80, 90]);
1126    }
1127
1128    #[test]
1129    fn iter_values_mut_rev_insert_only() {
1130        let mut arena = Arena::new();
1131        let _ = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1132        let mut iter_values_mut = arena.iter_mut().map(|&mut x| x).rev().collect::<Vec<_>>();
1133        iter_values_mut.sort_unstable();
1134        assert_eq!(iter_values_mut, [0, 10, 20, 30, 40, 50, 60, 70, 80, 90]);
1135    }
1136
1137    #[test]
1138    fn iter_values_mut_with_removal() {
1139        let mut arena = Arena::new();
1140        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1141        for i in (0..ins_values.len()).rev().step_by(3) {
1142            let key = ins_values.remove(i);
1143            arena.remove(key);
1144        }
1145        let mut iter_values_mut = arena.iter_mut().map(|&mut x| x).collect::<Vec<_>>();
1146        iter_values_mut.sort_unstable();
1147        assert_eq!(iter_values_mut, [10, 20, 40, 50, 70, 80]);
1148    }
1149
1150    #[test]
1151    fn iter_values_mut_rev_with_removal() {
1152        let mut arena = Arena::new();
1153        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1154        for i in (0..ins_values.len()).rev().step_by(3) {
1155            let key = ins_values.remove(i);
1156            arena.remove(key);
1157        }
1158        let mut iter_values_mut = arena.iter_mut().map(|&mut x| x).rev().collect::<Vec<_>>();
1159        iter_values_mut.sort_unstable();
1160        assert_eq!(iter_values_mut, [10, 20, 40, 50, 70, 80]);
1161    }
1162
1163    #[test]
1164    fn iter_values_mut_with_reinsertion() {
1165        let mut arena = Arena::new();
1166        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1167        for i in (0..ins_values.len()).rev().step_by(3) {
1168            let key = ins_values.remove(i);
1169            arena.remove(key);
1170        }
1171        for i in ins_values.len()..10 {
1172            ins_values.push(arena.insert(i * 100));
1173        }
1174        let mut iter_values_mut = arena.iter_mut().map(|&mut x| x).collect::<Vec<usize>>();
1175        let mut rev_iter_values_mut = arena.iter_mut().map(|&mut x| x).rev().collect::<Vec<usize>>();
1176
1177        // the order that the iter come out doesn't matter,
1178        // so put them in a canonical order
1179        iter_values_mut.sort_unstable();
1180        rev_iter_values_mut.sort_unstable();
1181
1182        assert_eq!(iter_values_mut, [10, 20, 40, 50, 70, 80, 600, 700, 800, 900]);
1183        assert_eq!(rev_iter_values_mut, [10, 20, 40, 50, 70, 80, 600, 700, 800, 900]);
1184    }
1185
1186    #[test]
1187    fn into_iter_values_insert_only() {
1188        let mut arena = Arena::new();
1189        let _ = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1190        let mut into_iter_values = arena.into_iter().collect::<Vec<_>>();
1191        into_iter_values.sort_unstable();
1192        assert_eq!(into_iter_values, [0, 10, 20, 30, 40, 50, 60, 70, 80, 90]);
1193    }
1194
1195    #[test]
1196    fn into_iter_values_rev_insert_only() {
1197        let mut arena = Arena::new();
1198        let _ = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1199        let mut into_iter_values = arena.into_iter().rev().collect::<Vec<_>>();
1200        into_iter_values.sort_unstable();
1201        assert_eq!(into_iter_values, [0, 10, 20, 30, 40, 50, 60, 70, 80, 90]);
1202    }
1203
1204    #[test]
1205    fn into_iter_values_with_removal() {
1206        let mut arena = Arena::new();
1207        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1208        for i in (0..ins_values.len()).rev().step_by(3) {
1209            let key = ins_values.remove(i);
1210            arena.remove(key);
1211        }
1212        let mut into_iter_values = arena.into_iter().collect::<Vec<_>>();
1213        into_iter_values.sort_unstable();
1214        assert_eq!(into_iter_values, [10, 20, 40, 50, 70, 80]);
1215    }
1216
1217    #[test]
1218    fn into_iter_values_rev_with_removal() {
1219        let mut arena = Arena::new();
1220        let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1221        for i in (0..ins_values.len()).rev().step_by(3) {
1222            let key = ins_values.remove(i);
1223            arena.remove(key);
1224        }
1225        let mut into_iter_values = arena.into_iter().rev().collect::<Vec<_>>();
1226        into_iter_values.sort_unstable();
1227        assert_eq!(into_iter_values, [10, 20, 40, 50, 70, 80]);
1228    }
1229
1230    #[test]
1231    fn into_iter_values_with_reinsertion() {
1232        let mk_arena = || {
1233            let mut arena = Arena::new();
1234            let mut ins_values = (0..10).map(|i| arena.insert(i * 10)).collect::<Vec<usize>>();
1235            for i in (0..ins_values.len()).rev().step_by(3) {
1236                let key = ins_values.remove(i);
1237                arena.remove(key);
1238            }
1239            for i in ins_values.len()..10 {
1240                ins_values.push(arena.insert(i * 100));
1241            }
1242            arena
1243        };
1244        let mut into_iter_values = mk_arena().into_iter().collect::<Vec<usize>>();
1245        let mut rev_into_iter_values = mk_arena().into_iter().rev().collect::<Vec<usize>>();
1246
1247        // the order that the iter come out doesn't matter,
1248        // so put them in a canonical order
1249        into_iter_values.sort_unstable();
1250        rev_into_iter_values.sort_unstable();
1251
1252        assert_eq!(into_iter_values, [10, 20, 40, 50, 70, 80, 600, 700, 800, 900]);
1253        assert_eq!(rev_into_iter_values, [10, 20, 40, 50, 70, 80, 600, 700, 800, 900]);
1254    }
1255}