1 use std::{ |
|
2 iter, |
|
3 mem::replace, |
|
4 ops::{Index, IndexMut}, |
|
5 }; |
|
6 |
|
7 pub struct IndexSlab<T> { |
|
8 data: Vec<Option<T>>, |
|
9 } |
|
10 |
|
11 impl<T> IndexSlab<T> { |
|
12 pub fn new() -> Self { |
|
13 Self { data: Vec::new() } |
|
14 } |
|
15 |
|
16 pub fn with_capacity(capacity: usize) -> Self { |
|
17 Self { |
|
18 data: Vec::with_capacity(capacity), |
|
19 } |
|
20 } |
|
21 |
|
22 pub fn insert(&mut self, index: usize, value: T) { |
|
23 if index >= self.data.len() { |
|
24 self.data.reserve(index - self.data.len() + 1); |
|
25 self.data.extend((self.data.len()..index).map(|_| None)); |
|
26 self.data.push(Some(value)) |
|
27 } else { |
|
28 self.data[index] = Some(value); |
|
29 } |
|
30 } |
|
31 |
|
32 pub fn contains(&self, index: usize) -> bool { |
|
33 self.data.get(index).and_then(|x| x.as_ref()).is_some() |
|
34 } |
|
35 |
|
36 pub fn remove(&mut self, index: usize) -> Option<T> { |
|
37 if let Some(x) = self.data.get_mut(index) { |
|
38 replace(x, None) |
|
39 } else { |
|
40 None |
|
41 } |
|
42 } |
|
43 |
|
44 pub fn iter(&self) -> impl Iterator<Item = (usize, &T)> { |
|
45 self.data |
|
46 .iter() |
|
47 .enumerate() |
|
48 .filter_map(|(index, opt)| opt.as_ref().and_then(|x| Some((index, x)))) |
|
49 } |
|
50 |
|
51 pub fn iter_mut(&mut self) -> impl Iterator<Item = (usize, &mut T)> { |
|
52 self.data |
|
53 .iter_mut() |
|
54 .enumerate() |
|
55 .filter_map(|(index, opt)| opt.as_mut().and_then(|x| Some((index, x)))) |
|
56 } |
|
57 } |
|
58 |
|
59 impl<T> Index<usize> for IndexSlab<T> { |
|
60 type Output = T; |
|
61 |
|
62 fn index(&self, index: usize) -> &Self::Output { |
|
63 self.data[index].as_ref().unwrap() |
|
64 } |
|
65 } |
|
66 |
|
67 impl<T> IndexMut<usize> for IndexSlab<T> { |
|
68 fn index_mut(&mut self, index: usize) -> &mut Self::Output { |
|
69 self.data[index].as_mut().unwrap() |
|
70 } |
|
71 } |
|