1
2use crate::{NodeLeaf, ContentTraits, TreeMetrics, Cursor, ContentTreeRaw};
3use rle::{Searchable, MergeIter, merge_items};
4
5#[derive(Debug)]
7pub struct ItemIterator<'a, E: ContentTraits, I: TreeMetrics<E>, const IE: usize, const LE: usize>(pub Cursor<'a, E, I, IE, LE>);
8
9impl<'a, E: ContentTraits + Searchable, I: TreeMetrics<E>, const IE: usize, const LE: usize> Iterator for ItemIterator<'a, E, I, IE, LE> {
10 type Item = E::Item;
11
12 fn next(&mut self) -> Option<Self::Item> {
13 if self.0.inner.idx == usize::MAX {
15 None
16 } else {
17 let entry = self.0.inner.get_raw_entry();
18 let len = entry.len();
19 let item = entry.at_offset(self.0.inner.offset);
20 self.0.inner.offset += 1;
21
22 if self.0.inner.offset >= len {
23 let has_next = self.0.inner.next_entry();
25 if !has_next {
26 self.0.inner.idx = usize::MAX;
28 }
29 }
30 Some(item)
31 }
32 }
33}
34
35#[derive(Debug)]
37pub struct NodeIter<'a, E: ContentTraits, I: TreeMetrics<E>, const IE: usize, const LE: usize>(Option<&'a NodeLeaf<E, I, IE, LE>>);
38
39impl<'a, E: ContentTraits, I: TreeMetrics<E>, const IE: usize, const LE: usize> Iterator for NodeIter<'a, E, I, IE, LE> {
40 type Item = &'a NodeLeaf<E, I, IE, LE>;
41
42 fn next(&mut self) -> Option<Self::Item> {
43 if let Some(leaf) = self.0 {
44 let this_ref = self.0;
45 self.0 = leaf.next.map(|ptr| unsafe { ptr.as_ref() });
46 this_ref
47 } else { None }
48 }
49}
50
51impl<E: ContentTraits, I: TreeMetrics<E>, const IE: usize, const LE: usize> ContentTreeRaw<E, I, IE, LE> {
52 pub fn raw_iter(&self) -> Cursor<E, I, IE, LE> { self.cursor_at_start() }
62
63 pub fn iter(&self) -> MergeIter<Cursor<E, I, IE, LE>> { merge_items(self.cursor_at_start()) }
66
67 pub fn item_iter(&self) -> ItemIterator<E, I, IE, LE> {
68 ItemIterator(self.raw_iter())
69 }
70
71 pub fn node_iter(&self) -> NodeIter<E, I, IE, LE> {
72 let leaf_ref = self.leaf_at_start();
73 NodeIter(if leaf_ref.num_entries > 0 { Some(leaf_ref) } else { None })
74 }
75}
76
77#[cfg(test)]
78mod test {
79 use crate::ContentTree;
80 use crate::testrange::TestRange;
81
82 #[test]
83 fn node_iter_smoke_test() {
84 let mut tree = ContentTree::new();
85
86 let mut iter = tree.node_iter();
87 assert!(iter.next().is_none());
88
89 tree.push(TestRange { id: 1000, len: 100, is_activated: true });
90
91 let mut iter = tree.node_iter();
92 let first = iter.next().unwrap();
93 assert_eq!(first.num_entries, 1);
94 assert!(iter.next().is_none());
95 }
96}