1use crate::{Checkpoint, Idx, IterIndexed, IterIndexedMut};
2
3pub struct Arena<T> {
11 items: Vec<T>,
12}
13
14impl<T> Arena<T> {
15 #[must_use]
17 pub const fn new() -> Self {
18 Self { items: Vec::new() }
19 }
20
21 #[must_use]
23 pub fn with_capacity(capacity: usize) -> Self {
24 Self {
25 items: Vec::with_capacity(capacity),
26 }
27 }
28
29 pub fn alloc(&mut self, value: T) -> Idx<T> {
33 let index = self.items.len();
34 self.items.push(value);
35 Idx::from_raw(index)
36 }
37
38 #[must_use]
44 pub fn get(&self, idx: Idx<T>) -> &T {
45 &self.items[idx.into_raw()]
46 }
47
48 #[must_use]
54 pub fn get_mut(&mut self, idx: Idx<T>) -> &mut T {
55 &mut self.items[idx.into_raw()]
56 }
57
58 #[must_use]
60 pub const fn len(&self) -> usize {
61 self.items.len()
62 }
63
64 #[must_use]
66 pub const fn is_empty(&self) -> bool {
67 self.items.is_empty()
68 }
69
70 #[must_use]
72 pub const fn capacity(&self) -> usize {
73 self.items.capacity()
74 }
75
76 #[must_use]
81 pub const fn checkpoint(&self) -> Checkpoint<T> {
82 Checkpoint::from_len(self.items.len())
83 }
84
85 pub fn rollback(&mut self, cp: Checkpoint<T>) {
94 assert!(
95 cp.len() <= self.items.len(),
96 "checkpoint {} beyond current length {}",
97 cp.len(),
98 self.items.len(),
99 );
100 self.items.truncate(cp.len());
101 }
102
103 pub fn reset(&mut self) {
107 self.items.clear();
108 }
109
110 pub fn iter(&self) -> std::slice::Iter<'_, T> {
112 self.items.iter()
113 }
114
115 pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, T> {
117 self.items.iter_mut()
118 }
119
120 pub fn alloc_extend(&mut self, iter: impl IntoIterator<Item = T>) -> Option<Idx<T>> {
127 let start = self.items.len();
128 self.items.extend(iter);
129 if self.items.len() > start {
130 Some(Idx::from_raw(start))
131 } else {
132 None
133 }
134 }
135
136 #[must_use]
141 pub const fn is_valid(&self, idx: Idx<T>) -> bool {
142 idx.into_raw() < self.items.len()
143 }
144
145 #[must_use]
148 pub fn try_get(&self, idx: Idx<T>) -> Option<&T> {
149 self.items.get(idx.into_raw())
150 }
151
152 #[must_use]
155 pub fn try_get_mut(&mut self, idx: Idx<T>) -> Option<&mut T> {
156 self.items.get_mut(idx.into_raw())
157 }
158
159 pub fn drain(&mut self) -> std::vec::Drain<'_, T> {
165 self.items.drain(..)
166 }
167
168 #[must_use]
170 pub fn iter_indexed(&self) -> IterIndexed<'_, T> {
171 IterIndexed::new(self.items.iter().enumerate())
172 }
173
174 pub fn iter_indexed_mut(&mut self) -> IterIndexedMut<'_, T> {
177 IterIndexedMut::new(self.items.iter_mut().enumerate())
178 }
179
180 pub fn reserve(&mut self, additional: usize) {
182 self.items.reserve(additional);
183 }
184
185 pub fn shrink_to_fit(&mut self) {
187 self.items.shrink_to_fit();
188 }
189}
190
191impl<T> Default for Arena<T> {
192 fn default() -> Self {
193 Self::new()
194 }
195}
196
197impl<T> std::ops::Index<Idx<T>> for Arena<T> {
198 type Output = T;
199
200 fn index(&self, idx: Idx<T>) -> &T {
201 self.get(idx)
202 }
203}
204
205impl<T> std::ops::IndexMut<Idx<T>> for Arena<T> {
206 fn index_mut(&mut self, idx: Idx<T>) -> &mut T {
207 self.get_mut(idx)
208 }
209}
210
211impl<'a, T> IntoIterator for &'a Arena<T> {
212 type Item = &'a T;
213 type IntoIter = std::slice::Iter<'a, T>;
214
215 fn into_iter(self) -> Self::IntoIter {
216 self.iter()
217 }
218}
219
220impl<'a, T> IntoIterator for &'a mut Arena<T> {
221 type Item = &'a mut T;
222 type IntoIter = std::slice::IterMut<'a, T>;
223
224 fn into_iter(self) -> Self::IntoIter {
225 self.iter_mut()
226 }
227}
228
229impl<T> Extend<T> for Arena<T> {
230 fn extend<I: IntoIterator<Item = T>>(&mut self, iter: I) {
231 self.items.extend(iter);
232 }
233}
234
235impl<T> std::iter::FromIterator<T> for Arena<T> {
236 fn from_iter<I: IntoIterator<Item = T>>(iter: I) -> Self {
237 Self {
238 items: iter.into_iter().collect(),
239 }
240 }
241}
242
243impl<T> IntoIterator for Arena<T> {
244 type Item = T;
245 type IntoIter = std::vec::IntoIter<T>;
246
247 fn into_iter(self) -> Self::IntoIter {
248 self.items.into_iter()
249 }
250}