1use alloc::vec::Vec;
11use core::num::NonZeroUsize;
12
13use crate::{DenseMap, EntryKey};
14
15pub trait DenseMapCollectionKey {
21 const VARIANT_COUNT: NonZeroUsize;
23
24 fn get_variant(&self) -> usize;
31
32 fn get_id(&self) -> usize;
34}
35
36impl<O> EntryKey for O
37where
38 O: DenseMapCollectionKey,
39{
40 fn get_key_index(&self) -> usize {
41 <O as DenseMapCollectionKey>::get_id(self)
42 }
43}
44
45pub struct VacantEntry<'a, K, T> {
47 entry: crate::VacantEntry<'a, K, T>,
48 count: &'a mut usize,
49}
50
51impl<'a, K, T> VacantEntry<'a, K, T> {
52 pub fn insert(self, value: T) -> &'a mut T
55 where
56 K: EntryKey,
57 {
58 let Self { entry, count } = self;
59 *count += 1;
60 entry.insert(value)
61 }
62
63 pub fn key(&self) -> &K {
66 self.entry.key()
67 }
68
69 pub fn into_key(self) -> K {
71 self.entry.into_key()
72 }
73
74 pub(crate) fn map_key<X, F>(self, f: F) -> VacantEntry<'a, X, T>
82 where
83 K: EntryKey,
84 X: EntryKey,
85 F: FnOnce(K) -> X,
86 {
87 let Self { entry, count } = self;
88 VacantEntry { entry: entry.map_key(f), count }
89 }
90}
91
92#[derive(Debug)]
94pub struct OccupiedEntry<'a, K, T> {
95 entry: crate::OccupiedEntry<'a, K, T>,
96 count: &'a mut usize,
97}
98
99impl<'a, K: EntryKey, T> OccupiedEntry<'a, K, T> {
100 pub fn key(&self) -> &K {
102 self.entry.key()
103 }
104
105 pub fn into_key(self) -> K {
107 self.entry.into_key()
108 }
109
110 pub fn get(&self) -> &T {
112 self.entry.get()
113 }
114
115 pub fn get_mut(&mut self) -> &mut T {
120 self.entry.get_mut()
121 }
122
123 pub fn into_mut(self) -> &'a mut T {
129 self.entry.into_mut()
130 }
131
132 pub fn insert(&mut self, value: T) -> T {
134 self.entry.insert(value)
135 }
136
137 pub fn remove(self) -> T {
139 let Self { entry, count } = self;
140 *count -= 1;
141 entry.remove()
142 }
143
144 pub(crate) fn map_key<X, F>(self, f: F) -> OccupiedEntry<'a, X, T>
152 where
153 K: EntryKey,
154 X: EntryKey,
155 F: FnOnce(K) -> X,
156 {
157 let Self { entry, count } = self;
158 OccupiedEntry { entry: entry.map_key(f), count }
159 }
160}
161
162pub enum Entry<'a, K, T> {
164 Vacant(VacantEntry<'a, K, T>),
166 Occupied(OccupiedEntry<'a, K, T>),
168}
169
170impl<'a, K: EntryKey, T> Entry<'a, K, T> {
171 pub fn key(&self) -> &K {
173 match self {
174 Entry::Occupied(e) => e.key(),
175 Entry::Vacant(e) => e.key(),
176 }
177 }
178
179 pub fn or_insert(self, default: T) -> &'a mut T
182 where
183 K: EntryKey,
184 {
185 self.or_insert_with(|| default)
186 }
187
188 pub fn or_insert_with<F: FnOnce() -> T>(self, f: F) -> &'a mut T {
191 match self {
192 Entry::Occupied(e) => e.into_mut(),
193 Entry::Vacant(e) => e.insert(f()),
194 }
195 }
196
197 pub fn or_default(self) -> &'a mut T
200 where
201 T: Default,
202 K: EntryKey,
203 {
204 self.or_insert_with(<T as Default>::default)
205 }
206
207 pub fn and_modify<F: FnOnce(&mut T)>(self, f: F) -> Self {
210 match self {
211 Entry::Occupied(mut e) => {
212 f(e.get_mut());
213 Entry::Occupied(e)
214 }
215 Entry::Vacant(e) => Entry::Vacant(e),
216 }
217 }
218
219 pub fn remove(self) -> Option<T> {
223 match self {
224 Entry::Vacant(_) => None,
225 Entry::Occupied(e) => Some(e.remove()),
226 }
227 }
228}
229
230struct SizeAugmentedIterator<I> {
235 wrapped: I,
236 remaining: usize,
237}
238
239impl<I: Iterator> Iterator for SizeAugmentedIterator<I> {
240 type Item = I::Item;
241
242 fn next(&mut self) -> Option<Self::Item> {
243 let Self { wrapped, remaining } = self;
244 match wrapped.next() {
245 Some(v) => {
246 *remaining -= 1;
247 Some(v)
248 }
249 None => {
250 assert_eq!(remaining, &0);
251 None
252 }
253 }
254 }
255
256 fn size_hint(&self) -> (usize, Option<usize>) {
257 (self.remaining, Some(self.remaining))
258 }
259}
260
261impl<I: Iterator> ExactSizeIterator for SizeAugmentedIterator<I> {}
262
263pub struct DenseMapCollection<K: DenseMapCollectionKey, T> {
269 data: Vec<DenseMap<T>>,
274 count: usize,
275 _marker: core::marker::PhantomData<K>,
276}
277
278impl<K: DenseMapCollectionKey, T> DenseMapCollection<K, T> {
279 pub fn new() -> Self {
281 let mut data = Vec::new();
282 data.resize_with(K::VARIANT_COUNT.get(), DenseMap::default);
283 Self { data, count: 0, _marker: core::marker::PhantomData }
284 }
285
286 fn get_map(&self, key: &K) -> &DenseMap<T> {
287 &self.data[key.get_variant()]
288 }
289
290 fn get_entry(&mut self, key: &K) -> Entry<'_, usize, T> {
291 let Self { data, count, _marker } = self;
292 match data[key.get_variant()].entry(key.get_id()) {
293 crate::Entry::Occupied(entry) => Entry::Occupied(OccupiedEntry { entry, count }),
294 crate::Entry::Vacant(entry) => Entry::Vacant(VacantEntry { entry, count }),
295 }
296 }
297
298 pub fn is_empty(&self) -> bool {
300 let Self { count, data: _, _marker } = self;
301 *count == 0
302 }
303
304 pub fn get(&self, key: &K) -> Option<&T> {
307 self.get_map(key).get(key.get_id())
308 }
309
310 pub fn get_mut(&mut self, key: &K) -> Option<&mut T> {
313 match self.get_entry(key) {
314 Entry::Occupied(e) => Some(e.into_mut()),
315 Entry::Vacant(_) => None,
316 }
317 }
318
319 pub fn remove(&mut self, key: &K) -> Option<T> {
323 match self.get_entry(key) {
324 Entry::Occupied(e) => Some(e.remove()),
325 Entry::Vacant(_) => None,
326 }
327 }
328
329 pub fn insert(&mut self, key: &K, item: T) -> Option<T> {
334 match self.get_entry(key) {
335 Entry::Occupied(mut e) => Some(e.insert(item)),
336 Entry::Vacant(e) => {
337 let _: &mut T = e.insert(item);
338 None
339 }
340 }
341 }
342
343 pub fn iter(&self) -> impl ExactSizeIterator<Item = &T> {
345 let Self { data, count, _marker } = self;
346 SizeAugmentedIterator {
347 wrapped: data.iter().flat_map(|m| m.key_ordered_iter()).map(|(_, v)| v),
348 remaining: *count,
349 }
350 }
351
352 pub fn iter_mut(&mut self) -> impl ExactSizeIterator<Item = &mut T> {
354 let Self { data, count, _marker } = self;
355 SizeAugmentedIterator {
356 wrapped: data.iter_mut().flat_map(|m| m.key_ordered_iter_mut()).map(|(_, v)| v),
357 remaining: *count,
358 }
359 }
360
361 pub fn iter_maps(&self) -> impl Iterator<Item = &DenseMap<T>> {
363 let Self { data, count: _, _marker } = self;
364 data.iter()
365 }
366
367 pub fn entry(&mut self, key: K) -> Entry<'_, K, T> {
370 match self.get_entry(&key) {
371 Entry::Occupied(e) => Entry::Occupied(e.map_key(|_| key)),
372 Entry::Vacant(e) => Entry::Vacant(e.map_key(|_| key)),
373 }
374 }
375
376 pub fn push_entry(&mut self, make_key: fn(usize) -> K, value: T) -> OccupiedEntry<'_, K, T> {
383 let Self { count, data, _marker } = self;
384 let variant = make_key(0).get_variant();
385 let entry = data[variant].push_entry(value);
386 *count += 1;
387
388 let entry = entry.map_key(make_key);
389
390 let entry_variant = entry.key().get_variant();
391 assert_eq!(
392 entry_variant, variant,
393 "key variant is inconsistent; got both {variant} and {entry_variant}"
394 );
395 OccupiedEntry { entry, count }
396 }
397}
398
399impl<K: DenseMapCollectionKey, T> Default for DenseMapCollection<K, T> {
400 fn default() -> Self {
401 Self::new()
402 }
403}
404
405#[cfg(test)]
406mod tests {
407 use alloc::collections::HashSet;
408
409 use super::*;
410 use crate::testutil::assert_empty;
411
412 #[derive(Copy, Clone, Eq, PartialEq, Debug)]
413 enum FakeVariants {
414 A,
415 B,
416 C,
417 }
418
419 #[derive(Copy, Clone, Eq, PartialEq, Debug)]
420 struct FakeKey {
421 id: usize,
422 var: FakeVariants,
423 }
424
425 impl FakeKey {
426 const fn new(id: usize, var: FakeVariants) -> Self {
427 Self { id, var }
428 }
429 }
430
431 impl DenseMapCollectionKey for FakeKey {
432 const VARIANT_COUNT: NonZeroUsize = NonZeroUsize::new(3).unwrap();
433
434 fn get_variant(&self) -> usize {
435 match self.var {
436 FakeVariants::A => 0,
437 FakeVariants::B => 1,
438 FakeVariants::C => 2,
439 }
440 }
441
442 fn get_id(&self) -> usize {
443 self.id
444 }
445 }
446
447 type TestCollection = DenseMapCollection<FakeKey, i32>;
448
449 const KEY_A: FakeKey = FakeKey::new(0, FakeVariants::A);
450 const KEY_B: FakeKey = FakeKey::new(2, FakeVariants::B);
451 const KEY_C: FakeKey = FakeKey::new(4, FakeVariants::C);
452
453 #[test]
454 fn test_insert_and_get() {
455 let mut t = TestCollection::new();
456 let DenseMapCollection { data, count, _marker } = &t;
457 assert_empty(data[0].key_ordered_iter());
458 assert_empty(data[1].key_ordered_iter());
459 assert_empty(data[2].key_ordered_iter());
460 assert_eq!(count, &0);
461
462 assert_eq!(t.insert(&KEY_A, 1), None);
463 let DenseMapCollection { data, count, _marker } = &t;
464 assert!(!data[0].is_empty());
465 assert_eq!(count, &1);
466
467 assert_eq!(t.insert(&KEY_B, 2), None);
468 let DenseMapCollection { data, count, _marker } = &t;
469 assert!(!data[1].is_empty());
470 assert_eq!(count, &2);
471
472 assert_eq!(*t.get(&KEY_A).unwrap(), 1);
473 assert_eq!(t.get(&KEY_C), None);
474
475 *t.get_mut(&KEY_B).unwrap() = 3;
476 assert_eq!(*t.get(&KEY_B).unwrap(), 3);
477 }
478
479 #[test]
480 fn test_remove() {
481 let mut t = TestCollection::new();
482 assert_eq!(t.insert(&KEY_B, 15), None);
483 assert_eq!(t.remove(&KEY_B).unwrap(), 15);
484 let DenseMapCollection { data: _, count, _marker } = &t;
485 assert_eq!(count, &0);
486
487 assert_eq!(t.remove(&KEY_B), None);
488 }
489
490 #[test]
491 fn test_iter() {
492 let mut t = TestCollection::new();
493 assert_eq!(t.insert(&KEY_A, 15), None);
494 assert_eq!(t.insert(&KEY_B, -5), None);
495 assert_eq!(t.insert(&KEY_C, -10), None);
496 let mut c = 0;
497 let mut sum = 0;
498 for i in t.iter() {
499 c += 1;
500 sum += *i;
501 }
502 assert_eq!(c, 3);
503 assert_eq!(sum, 0);
504 }
505
506 #[test]
507 fn test_iter_len() {
508 let mut t = TestCollection::new();
509 assert_eq!(t.insert(&KEY_A, 1), None);
510 assert_eq!(t.insert(&KEY_B, 1), None);
511 assert_eq!(t.insert(&KEY_C, 1), None);
512 assert_eq!(t.iter().len(), 3);
513 assert_eq!(t.remove(&KEY_A), Some(1));
514 assert_eq!(t.iter().len(), 2);
515 }
516
517 #[test]
518 fn test_is_empty() {
519 let mut t = TestCollection::new();
520 assert!(t.is_empty());
521 assert_eq!(t.insert(&KEY_B, 15), None);
522 assert!(!t.is_empty());
523 }
524
525 #[test]
526 fn test_iter_mut() {
527 let mut t = TestCollection::new();
528 assert_eq!(t.insert(&KEY_A, 15), None);
529 assert_eq!(t.insert(&KEY_B, -5), None);
530 assert_eq!(t.insert(&KEY_C, -10), None);
531 for i in t.iter_mut() {
532 *i *= 2;
533 }
534 assert_eq!(*t.get(&KEY_A).unwrap(), 30);
535 assert_eq!(*t.get(&KEY_B).unwrap(), -10);
536 assert_eq!(*t.get(&KEY_C).unwrap(), -20);
537 assert_eq!(t.iter_mut().len(), 3);
538 }
539
540 #[test]
541 fn test_entry() {
542 let mut t = TestCollection::new();
543 assert_eq!(*t.entry(KEY_A).or_insert(2), 2);
544 assert_eq!(
545 *t.entry(KEY_A)
546 .and_modify(|v| {
547 *v = 10;
548 })
549 .or_insert(5),
550 10
551 );
552 assert_eq!(
553 *t.entry(KEY_B)
554 .and_modify(|v| {
555 *v = 10;
556 })
557 .or_insert(5),
558 5
559 );
560 assert_eq!(*t.entry(KEY_C).or_insert_with(|| 7), 7);
561
562 assert_eq!(*t.entry(KEY_C).key(), KEY_C);
563 assert_eq!(*t.get(&KEY_A).unwrap(), 10);
564 assert_eq!(*t.get(&KEY_B).unwrap(), 5);
565 assert_eq!(*t.get(&KEY_C).unwrap(), 7);
566 }
567
568 #[test]
569 fn push_entry_valid() {
570 let mut t = TestCollection::new();
571 assert_eq!(t.insert(&KEY_A, 0), None);
572 assert_eq!(t.insert(&KEY_B, 1), None);
573 assert_eq!(t.insert(&KEY_C, 2), None);
574
575 let make_key = |index| FakeKey { id: index, var: FakeVariants::A };
576
577 {
578 let entry = t.push_entry(make_key, 30);
579 assert_eq!(entry.key(), &FakeKey { id: 1, var: FakeVariants::A });
580 assert_eq!(entry.get(), &30);
581 }
582
583 {
584 let entry = t.push_entry(make_key, 20);
585 assert_eq!(entry.key(), &FakeKey { id: 2, var: FakeVariants::A });
586 assert_eq!(entry.get(), &20);
587 }
588
589 assert_eq!(t.iter().collect::<HashSet<_>>(), HashSet::from([&0, &1, &2, &30, &20]));
590 }
591
592 #[test]
593 #[should_panic(expected = "variant is inconsistent")]
594 fn push_entry_invalid_key_fn() {
595 let mut t = TestCollection::new();
596 assert_eq!(t.insert(&KEY_A, 0), None);
597
598 let bad_make_key = |index| FakeKey {
599 id: index,
600 var: if index % 2 == 0 { FakeVariants::A } else { FakeVariants::B },
601 };
602
603 let _ = t.push_entry(bad_make_key, 1);
604 let _ = t.push_entry(bad_make_key, 2);
605 }
606}