prefix_trie/map/
mod.rs

1//! Implementation of the Prefix Map.
2
3use crate::{
4    inner::{Direction, DirectionForInsert, Node, Table},
5    Prefix,
6};
7
8// Include the entry and iter module last, to ensure correct docs.
9mod entry;
10mod iter;
11
12pub use entry::*;
13pub use iter::*;
14
15/// Prefix map implemented as a prefix tree.
16///
17/// You can perform union, intersection, and (covering) difference operations by first creating a
18/// view over the map using [`crate::AsView`] or [`crate::AsViewMut`].
19#[derive(Clone)]
20pub struct PrefixMap<P, T> {
21    pub(crate) table: Table<P, T>,
22    free: Vec<usize>,
23    count: usize,
24}
25
26impl<P, T> Default for PrefixMap<P, T>
27where
28    P: Prefix,
29{
30    fn default() -> Self {
31        Self {
32            table: Default::default(),
33            free: Vec::new(),
34            count: 0,
35        }
36    }
37}
38
39impl<P, T> PrefixMap<P, T>
40where
41    P: Prefix,
42{
43    /// Create an empty prefix map.
44    pub fn new() -> Self {
45        Self::default()
46    }
47
48    /// Returns the number of elements stored in `self`.
49    #[inline(always)]
50    pub fn len(&self) -> usize {
51        self.count
52    }
53
54    /// Returns `true` if the map contains no elements.
55    #[inline(always)]
56    pub fn is_empty(&self) -> bool {
57        self.count == 0
58    }
59
60    /// Get the value of an element by matching exactly on the prefix.
61    ///
62    /// ```
63    /// # use prefix_trie::*;
64    /// # #[cfg(feature = "ipnet")]
65    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
66    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
67    /// pm.insert("192.168.1.0/24".parse()?, 1);
68    /// assert_eq!(pm.get(&"192.168.1.0/24".parse()?), Some(&1));
69    /// assert_eq!(pm.get(&"192.168.2.0/24".parse()?), None);
70    /// assert_eq!(pm.get(&"192.168.0.0/23".parse()?), None);
71    /// assert_eq!(pm.get(&"192.168.1.128/25".parse()?), None);
72    /// # Ok(())
73    /// # }
74    /// # #[cfg(not(feature = "ipnet"))]
75    /// # fn main() {}
76    /// ```
77    pub fn get<'a>(&'a self, prefix: &P) -> Option<&'a T> {
78        let mut idx = 0;
79        loop {
80            match self.table.get_direction(idx, prefix) {
81                Direction::Reached => return self.table[idx].value.as_ref(),
82                Direction::Enter { next, .. } => idx = next,
83                Direction::Missing => return None,
84            }
85        }
86    }
87
88    /// Get a mutable reference to a value of an element by matching exactly on the prefix.
89    ///
90    /// ```
91    /// # use prefix_trie::*;
92    /// # #[cfg(feature = "ipnet")]
93    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
94    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
95    /// let prefix = "192.168.1.0/24".parse()?;
96    /// pm.insert(prefix, 1);
97    /// assert_eq!(pm.get(&prefix), Some(&1));
98    /// *pm.get_mut(&prefix).unwrap() += 1;
99    /// assert_eq!(pm.get(&prefix), Some(&2));
100    /// # Ok(())
101    /// # }
102    /// # #[cfg(not(feature = "ipnet"))]
103    /// # fn main() {}
104    /// ```
105    pub fn get_mut<'a>(&'a mut self, prefix: &P) -> Option<&'a mut T> {
106        let mut idx = 0;
107        loop {
108            match self.table.get_direction(idx, prefix) {
109                Direction::Reached => return self.table[idx].value.as_mut(),
110                Direction::Enter { next, .. } => idx = next,
111                Direction::Missing => return None,
112            }
113        }
114    }
115
116    /// Get the value of an element by matching exactly on the prefix. Notice, that the returned
117    /// prefix may differ from the one provided in the host-part of the address.
118    ///
119    /// ```
120    /// # use prefix_trie::*;
121    /// # #[cfg(feature = "ipnet")]
122    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
123    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
124    /// let prefix = "192.168.1.0/24".parse()?;
125    /// pm.insert(prefix, 1);
126    /// assert_eq!(pm.get_key_value(&prefix), Some((&prefix, &1)));
127    /// # Ok(())
128    /// # }
129    /// # #[cfg(not(feature = "ipnet"))]
130    /// # fn main() {}
131    /// ```
132    pub fn get_key_value<'a>(&'a self, prefix: &P) -> Option<(&'a P, &'a T)> {
133        let mut idx = 0;
134        loop {
135            match self.table.get_direction(idx, prefix) {
136                Direction::Reached => return self.table[idx].prefix_value(),
137                Direction::Enter { next, .. } => idx = next,
138                Direction::Missing => return None,
139            }
140        }
141    }
142
143    /// Get a value of an element by using longest prefix matching
144    ///
145    /// ```
146    /// # use prefix_trie::*;
147    /// # #[cfg(feature = "ipnet")]
148    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
149    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
150    /// pm.insert("192.168.1.0/24".parse()?, 1);
151    /// pm.insert("192.168.0.0/23".parse()?, 2);
152    /// assert_eq!(pm.get_lpm(&"192.168.1.1/32".parse()?), Some((&"192.168.1.0/24".parse()?, &1)));
153    /// assert_eq!(pm.get_lpm(&"192.168.1.0/24".parse()?), Some((&"192.168.1.0/24".parse()?, &1)));
154    /// assert_eq!(pm.get_lpm(&"192.168.0.0/24".parse()?), Some((&"192.168.0.0/23".parse()?, &2)));
155    /// assert_eq!(pm.get_lpm(&"192.168.2.0/24".parse()?), None);
156    /// # Ok(())
157    /// # }
158    /// # #[cfg(not(feature = "ipnet"))]
159    /// # fn main() {}
160    /// ```
161    pub fn get_lpm<'a>(&'a self, prefix: &P) -> Option<(&'a P, &'a T)> {
162        let mut idx = 0;
163        let mut best_match: Option<(&P, &T)> = None;
164        loop {
165            best_match = self.table[idx].prefix_value().or(best_match);
166            match self.table.get_direction(idx, prefix) {
167                Direction::Enter { next, .. } => idx = next,
168                _ => return best_match,
169            }
170        }
171    }
172
173    /// Get a mutable reference to a value of an element by using longest prefix matching
174    ///
175    /// ```
176    /// # use prefix_trie::*;
177    /// # #[cfg(feature = "ipnet")]
178    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
179    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
180    /// pm.insert("192.168.1.0/24".parse()?, 1);
181    /// pm.insert("192.168.0.0/23".parse()?, 2);
182    /// assert_eq!(pm.get_lpm(&"192.168.1.1/32".parse()?), Some((&"192.168.1.0/24".parse()?, &1)));
183    /// *pm.get_lpm_mut(&"192.168.1.64/26".parse()?).unwrap().1 += 1;
184    /// assert_eq!(pm.get_lpm(&"192.168.1.1/32".parse()?), Some((&"192.168.1.0/24".parse()?, &2)));
185    /// # Ok(())
186    /// # }
187    /// # #[cfg(not(feature = "ipnet"))]
188    /// # fn main() {}
189    /// ```
190    pub fn get_lpm_mut<'a>(&'a mut self, prefix: &P) -> Option<(&'a P, &'a mut T)> {
191        let mut idx = 0;
192        let mut best_match: Option<usize> = None;
193        loop {
194            best_match = if self.table[idx].value.is_some() {
195                Some(idx)
196            } else {
197                best_match
198            };
199            match self.table.get_direction(idx, prefix) {
200                Direction::Enter { next, .. } => idx = next,
201                _ => break,
202            }
203        }
204        if let Some(idx) = best_match {
205            self.table[idx].prefix_value_mut()
206        } else {
207            None
208        }
209    }
210
211    /// Check if a key is present in the datastructure.
212    ///
213    /// ```
214    /// # use prefix_trie::*;
215    /// # #[cfg(feature = "ipnet")]
216    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
217    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
218    /// pm.insert("192.168.1.0/24".parse()?, 1);
219    /// assert!(pm.contains_key(&"192.168.1.0/24".parse()?));
220    /// assert!(!pm.contains_key(&"192.168.2.0/24".parse()?));
221    /// assert!(!pm.contains_key(&"192.168.0.0/23".parse()?));
222    /// assert!(!pm.contains_key(&"192.168.1.128/25".parse()?));
223    /// # Ok(())
224    /// # }
225    /// # #[cfg(not(feature = "ipnet"))]
226    /// # fn main() {}
227    /// ```
228    pub fn contains_key(&self, prefix: &P) -> bool {
229        let mut idx = 0;
230        loop {
231            match self.table.get_direction(idx, prefix) {
232                Direction::Reached => return self.table[idx].value.is_some(),
233                Direction::Enter { next, .. } => idx = next,
234                Direction::Missing => return false,
235            }
236        }
237    }
238
239    /// Get the longest prefix in the datastructure that matches the given `prefix`.
240    ///
241    /// ```
242    /// # use prefix_trie::*;
243    /// # #[cfg(feature = "ipnet")]
244    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
245    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
246    /// pm.insert("192.168.1.0/24".parse()?, 1);
247    /// pm.insert("192.168.0.0/23".parse()?, 2);
248    /// assert_eq!(pm.get_lpm_prefix(&"192.168.1.1/32".parse()?), Some(&"192.168.1.0/24".parse()?));
249    /// assert_eq!(pm.get_lpm_prefix(&"192.168.1.0/24".parse()?), Some(&"192.168.1.0/24".parse()?));
250    /// assert_eq!(pm.get_lpm_prefix(&"192.168.0.0/24".parse()?), Some(&"192.168.0.0/23".parse()?));
251    /// assert_eq!(pm.get_lpm_prefix(&"192.168.2.0/24".parse()?), None);
252    /// # Ok(())
253    /// # }
254    /// # #[cfg(not(feature = "ipnet"))]
255    /// # fn main() {}
256    /// ```
257    pub fn get_lpm_prefix<'a>(&'a self, prefix: &P) -> Option<&'a P> {
258        let mut idx = 0;
259        let mut best_match: Option<&P> = None;
260        loop {
261            best_match = self.table[idx]
262                .prefix_value()
263                .map(|(p, _)| p)
264                .or(best_match);
265            match self.table.get_direction(idx, prefix) {
266                Direction::Enter { next, .. } => idx = next,
267                _ => return best_match,
268            }
269        }
270    }
271
272    /// Get a value of an element by using shortest prefix matching.
273    ///
274    /// ```
275    /// # use prefix_trie::*;
276    /// # #[cfg(feature = "ipnet")]
277    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
278    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
279    /// pm.insert("192.168.1.0/24".parse()?, 1);
280    /// pm.insert("192.168.0.0/23".parse()?, 2);
281    /// assert_eq!(pm.get_spm(&"192.168.1.1/32".parse()?), Some((&"192.168.0.0/23".parse()?, &2)));
282    /// assert_eq!(pm.get_spm(&"192.168.1.0/24".parse()?), Some((&"192.168.0.0/23".parse()?, &2)));
283    /// assert_eq!(pm.get_spm(&"192.168.0.0/23".parse()?), Some((&"192.168.0.0/23".parse()?, &2)));
284    /// assert_eq!(pm.get_spm(&"192.168.2.0/24".parse()?), None);
285    /// # Ok(())
286    /// # }
287    /// # #[cfg(not(feature = "ipnet"))]
288    /// # fn main() {}
289    pub fn get_spm<'a>(&'a self, prefix: &P) -> Option<(&'a P, &'a T)> {
290        // Handle the special case, where the root is populated
291        if let Some(x) = self.table[0].prefix_value() {
292            return Some(x);
293        }
294        let mut idx = 0;
295        loop {
296            match self.table.get_direction(idx, prefix) {
297                Direction::Reached => return self.table[idx].prefix_value(),
298                Direction::Enter { next, .. } => {
299                    // Go until the first node with a value
300                    match self.table[next].prefix_value() {
301                        Some(x) => return Some(x),
302                        None => idx = next,
303                    }
304                }
305                Direction::Missing => return None,
306            }
307        }
308    }
309
310    /// Get the shortest prefix in the datastructure that contains the given `prefix`.
311    ///
312    /// ```
313    /// # use prefix_trie::*;
314    /// # #[cfg(feature = "ipnet")]
315    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
316    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
317    /// pm.insert("192.168.1.1/24".parse()?, 1);
318    /// pm.insert("192.168.0.0/23".parse()?, 2);
319    /// assert_eq!(pm.get_spm_prefix(&"192.168.1.1/32".parse()?), Some(&"192.168.0.0/23".parse()?));
320    /// assert_eq!(pm.get_spm_prefix(&"192.168.1.0/24".parse()?), Some(&"192.168.0.0/23".parse()?));
321    /// assert_eq!(pm.get_spm_prefix(&"192.168.0.0/23".parse()?), Some(&"192.168.0.0/23".parse()?));
322    /// assert_eq!(pm.get_spm_prefix(&"192.168.2.0/24".parse()?), None);
323    /// # Ok(())
324    /// # }
325    /// # #[cfg(not(feature = "ipnet"))]
326    /// # fn main() {}
327    pub fn get_spm_prefix<'a>(&'a self, prefix: &P) -> Option<&'a P> {
328        self.get_spm(prefix).map(|(p, _)| p)
329    }
330
331    /// Insert a new item into the prefix-map. This function may return any value that existed
332    /// before.
333    ///
334    /// ```
335    /// # use prefix_trie::*;
336    /// # #[cfg(feature = "ipnet")]
337    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
338    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
339    /// assert_eq!(pm.insert("192.168.0.0/23".parse()?, 1), None);
340    /// assert_eq!(pm.insert("192.168.1.0/24".parse()?, 2), None);
341    /// assert_eq!(pm.insert("192.168.1.0/24".parse()?, 3), Some(2));
342    /// # Ok(())
343    /// # }
344    /// # #[cfg(not(feature = "ipnet"))]
345    /// # fn main() {}
346    /// ```
347    ///
348    /// You can store additional information in the host-part of the prefix. This information is
349    /// preserved in the map, and can be accessed with [`Self::get_key_value`]. In case the node
350    /// already exists in the tree, its prefix will be replaced by the provided argument. The
351    /// following example illustrates this:
352    ///
353    /// ```
354    /// # use prefix_trie::*;
355    /// # #[cfg(feature = "ipnet")]
356    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
357    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
358    ///
359    /// pm.insert("192.168.0.1/24".parse()?, 1);
360    /// assert_eq!(
361    ///     pm.get_key_value(&"192.168.0.0/24".parse()?), // notice that the host part is zero
362    ///     Some((&"192.168.0.1/24".parse()?, &1))
363    /// );
364    ///
365    /// pm.insert("192.168.0.100/24".parse()?, 5);
366    /// assert_eq!(
367    ///     pm.get_key_value(&"192.168.0.0/24".parse()?),
368    ///     Some((&"192.168.0.100/24".parse()?, &5)) // `insert` updates the host part as well.
369    /// );
370    /// # Ok(())
371    /// # }
372    /// # #[cfg(not(feature = "ipnet"))]
373    /// # fn main() {}
374    /// ```
375    pub fn insert(&mut self, prefix: P, value: T) -> Option<T> {
376        let mut idx = 0;
377        loop {
378            match self.table.get_direction_for_insert(idx, &prefix) {
379                DirectionForInsert::Enter { next, .. } => idx = next,
380                DirectionForInsert::Reached => {
381                    let mut inc = 0;
382                    let node = &mut self.table[idx];
383                    // replace the prefix
384                    node.prefix = prefix;
385                    let old_value = node.value.take();
386                    if old_value.is_none() {
387                        inc = 1;
388                    }
389                    node.value = Some(value);
390                    self.count += inc;
391                    return old_value;
392                }
393                DirectionForInsert::NewLeaf { right } => {
394                    let new = self.new_node(prefix, Some(value));
395                    self.table.set_child(idx, new, right);
396                    return None;
397                }
398                DirectionForInsert::NewChild { right, child_right } => {
399                    let new = self.new_node(prefix, Some(value));
400                    let child = self.table.set_child(idx, new, right).unwrap();
401                    self.table.set_child(new, child, child_right);
402                    return None;
403                }
404                DirectionForInsert::NewBranch {
405                    branch_prefix,
406                    right,
407                    prefix_right,
408                } => {
409                    let branch = self.new_node(branch_prefix, None);
410                    let new = self.new_node(prefix, Some(value));
411                    let child = self.table.set_child(idx, branch, right).unwrap();
412                    self.table.set_child(branch, new, prefix_right);
413                    self.table.set_child(branch, child, !prefix_right);
414                    return None;
415                }
416            }
417        }
418    }
419
420    /// Gets the given key’s corresponding entry in the map for in-place manipulation. In case you
421    /// eventually insert an element into the map, this operation will also replace the prefix in
422    /// the node with the existing one. That is if you store additional information in the host part
423    /// of the address (the one that is masked out). See the documentation of the individual
424    /// functions of [`Entry`], [`OccupiedEntry`], and [`VacantEntry`].
425    ///
426    /// ```
427    /// # use prefix_trie::*;
428    /// # #[cfg(feature = "ipnet")]
429    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
430    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
431    /// pm.insert("192.168.0.0/23".parse()?, vec![1]);
432    /// pm.entry("192.168.0.0/23".parse()?).or_default().push(2);
433    /// pm.entry("192.168.0.0/24".parse()?).or_default().push(3);
434    /// assert_eq!(pm.get(&"192.168.0.0/23".parse()?), Some(&vec![1, 2]));
435    /// assert_eq!(pm.get(&"192.168.0.0/24".parse()?), Some(&vec![3]));
436    /// # Ok(())
437    /// # }
438    /// # #[cfg(not(feature = "ipnet"))]
439    /// # fn main() {}
440    /// ```
441    pub fn entry(&mut self, prefix: P) -> Entry<'_, P, T> {
442        let mut idx = 0;
443        loop {
444            match self.table.get_direction_for_insert(idx, &prefix) {
445                DirectionForInsert::Enter { next, .. } => idx = next,
446                DirectionForInsert::Reached if self.table[idx].value.is_some() => {
447                    return Entry::Occupied(OccupiedEntry {
448                        node: &mut self.table[idx],
449                        prefix,
450                    })
451                }
452                direction => {
453                    return Entry::Vacant(VacantEntry {
454                        map: self,
455                        prefix,
456                        idx,
457                        direction,
458                    })
459                }
460            }
461        }
462    }
463
464    /// Removes a key from the map, returning the value at the key if the key was previously in the
465    /// map. In contrast to [`Self::remove_keep_tree`], this operation will modify the tree
466    /// structure. As a result, this operation takes longer than `remove_keep_tree`, as does
467    /// inserting the same element again. However, future reads may be faster as less nodes need to
468    /// be traversed. Further, it reduces the memory footprint to its minimum.
469    ///
470    /// ```
471    /// # use prefix_trie::*;
472    /// # #[cfg(feature = "ipnet")]
473    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
474    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
475    /// let prefix = "192.168.1.0/24".parse()?;
476    /// pm.insert(prefix, 1);
477    /// assert_eq!(pm.get(&prefix), Some(&1));
478    /// assert_eq!(pm.remove(&prefix), Some(1));
479    /// assert_eq!(pm.get(&prefix), None);
480    /// # Ok(())
481    /// # }
482    /// # #[cfg(not(feature = "ipnet"))]
483    /// # fn main() {}
484    /// ```
485    pub fn remove(&mut self, prefix: &P) -> Option<T> {
486        let mut idx = 0;
487        let mut grandparent = None;
488        let mut grandparent_right = false;
489        let mut parent = None;
490        let mut parent_right = false;
491        // first, search for the element
492        loop {
493            match self.table.get_direction(idx, prefix) {
494                Direction::Reached => break,
495                Direction::Enter { next, right } => {
496                    grandparent_right = parent_right;
497                    parent_right = right;
498                    grandparent = parent;
499                    parent = Some(idx);
500                    idx = next;
501                }
502                Direction::Missing => return None,
503            }
504        }
505        self._remove_node(idx, parent, parent_right, grandparent, grandparent_right)
506            .0
507    }
508
509    /// Removes a key from the map, returning the value at the key if the key was previously in the
510    /// map. In contrast to [`Self::remove`], his operation will keep the tree structure as is, but
511    /// only remove the element from it. This allows any future `insert` on the same prefix to be
512    /// faster. However future reads from the tree might be a bit slower because they need to
513    /// traverse more nodes.
514    ///
515    /// ```
516    /// # use prefix_trie::*;
517    /// # #[cfg(feature = "ipnet")]
518    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
519    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
520    /// let prefix = "192.168.1.0/24".parse()?;
521    /// pm.insert(prefix, 1);
522    /// assert_eq!(pm.get(&prefix), Some(&1));
523    /// assert_eq!(pm.remove_keep_tree(&prefix), Some(1));
524    /// assert_eq!(pm.get(&prefix), None);
525    ///
526    /// // future inserts of the same key are now faster!
527    /// pm.insert(prefix, 1);
528    /// # Ok(())
529    /// # }
530    /// # #[cfg(not(feature = "ipnet"))]
531    /// # fn main() {}
532    /// ```
533    pub fn remove_keep_tree(&mut self, prefix: &P) -> Option<T> {
534        let mut idx = 0;
535        let value = loop {
536            match self.table.get_direction(idx, prefix) {
537                Direction::Reached => break self.table[idx].value.take(),
538                Direction::Enter { next, .. } => idx = next,
539                Direction::Missing => break None,
540            }
541        };
542
543        // decrease the count if the value is something
544        if value.is_some() {
545            self.count -= 1;
546        }
547
548        value
549    }
550
551    /// Remove all entries that are contained within `prefix`. This will change the tree
552    /// structure. This operation is `O(n)`, as the entries must be freed up one-by-one.
553    ///
554    /// ```
555    /// # use prefix_trie::*;
556    /// # #[cfg(feature = "ipnet")]
557    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
558    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
559    /// pm.insert("192.168.0.0/22".parse()?, 1);
560    /// pm.insert("192.168.0.0/23".parse()?, 2);
561    /// pm.insert("192.168.0.0/24".parse()?, 3);
562    /// pm.insert("192.168.2.0/23".parse()?, 4);
563    /// pm.insert("192.168.2.0/24".parse()?, 5);
564    /// pm.remove_children(&"192.168.0.0/23".parse()?);
565    /// assert_eq!(pm.get(&"192.168.0.0/23".parse()?), None);
566    /// assert_eq!(pm.get(&"192.168.0.0/24".parse()?), None);
567    /// assert_eq!(pm.get(&"192.168.2.0/23".parse()?), Some(&4));
568    /// assert_eq!(pm.get(&"192.168.2.0/24".parse()?), Some(&5));
569    /// # Ok(())
570    /// # }
571    /// # #[cfg(not(feature = "ipnet"))]
572    /// # fn main() {}
573    /// ```
574    pub fn remove_children(&mut self, prefix: &P) {
575        if prefix.prefix_len() == 0 {
576            return self.clear();
577        }
578        let mut parent_right = false;
579        let mut parent = 0;
580        let mut idx = 0;
581        loop {
582            match self.table.get_direction_for_insert(idx, prefix) {
583                DirectionForInsert::Reached => {
584                    return self._do_remove_children(parent, parent_right)
585                }
586                DirectionForInsert::Enter { next, right } => {
587                    parent_right = right;
588                    parent = idx;
589                    idx = next
590                }
591                DirectionForInsert::NewLeaf { .. } | DirectionForInsert::NewBranch { .. } => return,
592                DirectionForInsert::NewChild { right, .. } => {
593                    return self._do_remove_children(idx, right)
594                }
595            }
596        }
597    }
598
599    /// Clear the map but keep the allocated memory.
600    ///
601    /// ```
602    /// # use prefix_trie::*;
603    /// # #[cfg(feature = "ipnet")]
604    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
605    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
606    /// pm.insert("192.168.0.0/24".parse()?, 1);
607    /// pm.insert("192.168.1.0/24".parse()?, 2);
608    /// pm.clear();
609    /// assert_eq!(pm.get(&"192.168.0.0/24".parse()?), None);
610    /// assert_eq!(pm.get(&"192.168.1.0/24".parse()?), None);
611    /// # Ok(())
612    /// # }
613    /// # #[cfg(not(feature = "ipnet"))]
614    /// # fn main() {}
615    /// ```
616    pub fn clear(&mut self) {
617        self.table.as_mut().clear();
618        self.free.clear();
619        self.table.as_mut().push(Node {
620            prefix: P::zero(),
621            value: None,
622            left: None,
623            right: None,
624        });
625        self.count = 0;
626    }
627
628    /// Keep only the elements in the map that satisfy the given condition `f`.
629    ///
630    /// ```
631    /// # use prefix_trie::*;
632    /// # #[cfg(feature = "ipnet")]
633    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
634    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
635    /// pm.insert("192.168.0.0/24".parse()?, 1);
636    /// pm.insert("192.168.1.0/24".parse()?, 2);
637    /// pm.insert("192.168.2.0/24".parse()?, 3);
638    /// pm.insert("192.168.2.0/25".parse()?, 4);
639    /// pm.retain(|_, t| *t % 2 == 0);
640    /// assert_eq!(pm.get(&"192.168.0.0/24".parse()?), None);
641    /// assert_eq!(pm.get(&"192.168.1.0/24".parse()?), Some(&2));
642    /// assert_eq!(pm.get(&"192.168.2.0/24".parse()?), None);
643    /// assert_eq!(pm.get(&"192.168.2.0/25".parse()?), Some(&4));
644    /// # Ok(())
645    /// # }
646    /// # #[cfg(not(feature = "ipnet"))]
647    /// # fn main() {}
648    /// ```
649    pub fn retain<F>(&mut self, f: F)
650    where
651        F: FnMut(&P, &T) -> bool,
652    {
653        self._retain(0, None, false, None, false, f);
654    }
655
656    /// Iterate over all entries in the map that covers the given `prefix` (including `prefix`
657    /// itself if that is present in the map). The returned iterator yields `(&'a P, &'a T)`.
658    ///
659    /// The iterator will always yield elements ordered by their prefix length, i.e., their depth in
660    /// the tree.
661    ///
662    /// ```
663    /// # use prefix_trie::*;
664    /// # #[cfg(feature = "ipnet")]
665    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
666    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
667    /// let p0 = "10.0.0.0/8".parse()?;
668    /// let p1 = "10.1.0.0/16".parse()?;
669    /// let p2 = "10.1.1.0/24".parse()?;
670    /// pm.insert(p0, 0);
671    /// pm.insert(p1, 1);
672    /// pm.insert(p2, 2);
673    /// pm.insert("10.1.2.0/24".parse()?, 3); // disjoint prefixes are not covered
674    /// pm.insert("10.1.1.0/25".parse()?, 4); // more specific prefixes are not covered
675    /// pm.insert("11.0.0.0/8".parse()?, 5);  // Branch points that don't contain values are skipped
676    /// assert_eq!(
677    ///     pm.cover(&p2).collect::<Vec<_>>(),
678    ///     vec![(&p0, &0), (&p1, &1), (&p2, &2)]
679    /// );
680    /// # Ok(())
681    /// # }
682    /// # #[cfg(not(feature = "ipnet"))]
683    /// # fn main() {}
684    /// ```
685    ///
686    /// This function also yields the root note *if* it is part of the map:
687    ///
688    /// ```
689    /// # use prefix_trie::*;
690    /// # #[cfg(feature = "ipnet")]
691    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
692    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
693    /// let root = "0.0.0.0/0".parse()?;
694    /// pm.insert(root, 0);
695    /// assert_eq!(pm.cover(&"10.0.0.0/8".parse()?).collect::<Vec<_>>(), vec![(&root, &0)]);
696    /// # Ok(())
697    /// # }
698    /// # #[cfg(not(feature = "ipnet"))]
699    /// # fn main() {}
700    /// ```
701    pub fn cover<'a, 'p>(&'a self, prefix: &'p P) -> Cover<'a, 'p, P, T> {
702        Cover {
703            table: &self.table,
704            idx: None,
705            prefix,
706        }
707    }
708
709    /// Iterate over all keys (prefixes) in the map that covers the given `prefix` (including
710    /// `prefix` itself if that is present in the map). The returned iterator yields `&'a P`.
711    ///
712    /// The iterator will always yield elements ordered by their prefix length, i.e., their depth in
713    /// the tree.
714    ///
715    /// ```
716    /// # use prefix_trie::*;
717    /// # #[cfg(feature = "ipnet")]
718    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
719    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
720    /// let p0 = "10.0.0.0/8".parse()?;
721    /// let p1 = "10.1.0.0/16".parse()?;
722    /// let p2 = "10.1.1.0/24".parse()?;
723    /// pm.insert(p0, 0);
724    /// pm.insert(p1, 1);
725    /// pm.insert(p2, 2);
726    /// pm.insert("10.1.2.0/24".parse()?, 3); // disjoint prefixes are not covered
727    /// pm.insert("10.1.1.0/25".parse()?, 4); // more specific prefixes are not covered
728    /// pm.insert("11.0.0.0/8".parse()?, 5);  // Branch points that don't contain values are skipped
729    /// assert_eq!(pm.cover_keys(&p2).collect::<Vec<_>>(), vec![&p0, &p1, &p2]);
730    /// # Ok(())
731    /// # }
732    /// # #[cfg(not(feature = "ipnet"))]
733    /// # fn main() {}
734    /// ```
735    pub fn cover_keys<'a, 'p>(&'a self, prefix: &'p P) -> CoverKeys<'a, 'p, P, T> {
736        CoverKeys(Cover {
737            table: &self.table,
738            idx: None,
739            prefix,
740        })
741    }
742
743    /// Iterate over all values in the map that covers the given `prefix` (including `prefix`
744    /// itself if that is present in the map). The returned iterator yields `&'a T`.
745    ///
746    /// The iterator will always yield elements ordered by their prefix length, i.e., their depth in
747    /// the tree.
748    ///
749    /// ```
750    /// # use prefix_trie::*;
751    /// # #[cfg(feature = "ipnet")]
752    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
753    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
754    /// let p0 = "10.0.0.0/8".parse()?;
755    /// let p1 = "10.1.0.0/16".parse()?;
756    /// let p2 = "10.1.1.0/24".parse()?;
757    /// pm.insert(p0, 0);
758    /// pm.insert(p1, 1);
759    /// pm.insert(p2, 2);
760    /// pm.insert("10.1.2.0/24".parse()?, 3); // disjoint prefixes are not covered
761    /// pm.insert("10.1.1.0/25".parse()?, 4); // more specific prefixes are not covered
762    /// pm.insert("11.0.0.0/8".parse()?, 5);  // Branch points that don't contain values are skipped
763    /// assert_eq!(pm.cover_values(&p2).collect::<Vec<_>>(), vec![&0, &1, &2]);
764    /// # Ok(())
765    /// # }
766    /// # #[cfg(not(feature = "ipnet"))]
767    /// # fn main() {}
768    /// ```
769    pub fn cover_values<'a, 'p>(&'a self, prefix: &'p P) -> CoverValues<'a, 'p, P, T> {
770        CoverValues(Cover {
771            table: &self.table,
772            idx: None,
773            prefix,
774        })
775    }
776}
777
778impl<P, T> PrefixMap<P, T> {
779    /// An iterator visiting all key-value pairs in lexicographic order. The iterator element type
780    /// is `(&P, &T)`.
781    ///
782    /// ```
783    /// # use prefix_trie::*;
784    /// # #[cfg(feature = "ipnet")]
785    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
786    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
787    /// pm.insert("192.168.0.0/22".parse()?, 1);
788    /// pm.insert("192.168.0.0/23".parse()?, 2);
789    /// pm.insert("192.168.2.0/23".parse()?, 3);
790    /// pm.insert("192.168.0.0/24".parse()?, 4);
791    /// pm.insert("192.168.2.0/24".parse()?, 5);
792    /// assert_eq!(
793    ///     pm.iter().collect::<Vec<_>>(),
794    ///     vec![
795    ///         (&"192.168.0.0/22".parse()?, &1),
796    ///         (&"192.168.0.0/23".parse()?, &2),
797    ///         (&"192.168.0.0/24".parse()?, &4),
798    ///         (&"192.168.2.0/23".parse()?, &3),
799    ///         (&"192.168.2.0/24".parse()?, &5),
800    ///     ]
801    /// );
802    /// # Ok(())
803    /// # }
804    /// # #[cfg(not(feature = "ipnet"))]
805    /// # fn main() {}
806    /// ```
807    #[inline(always)]
808    pub fn iter(&self) -> Iter<'_, P, T> {
809        self.into_iter()
810    }
811
812    /// Get a mutable iterator over all key-value pairs. The order of this iterator is lexicographic.
813    pub fn iter_mut(&mut self) -> IterMut<'_, P, T> {
814        // Safety: We get the pointer to the table by and construct the `IterMut`. Its lifetime is
815        // now tied to the mutable borrow of `self`, so we are allowed to access elements of that
816        // table mutably.
817        unsafe { IterMut::new(&self.table, vec![0]) }
818    }
819
820    /// An iterator visiting all keys in lexicographic order. The iterator element type is `&P`.
821    ///
822    /// ```
823    /// # use prefix_trie::*;
824    /// # #[cfg(feature = "ipnet")]
825    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
826    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
827    /// pm.insert("192.168.0.0/22".parse()?, 1);
828    /// pm.insert("192.168.0.0/23".parse()?, 2);
829    /// pm.insert("192.168.2.0/23".parse()?, 3);
830    /// pm.insert("192.168.0.0/24".parse()?, 4);
831    /// pm.insert("192.168.2.0/24".parse()?, 5);
832    /// assert_eq!(
833    ///     pm.keys().collect::<Vec<_>>(),
834    ///     vec![
835    ///         &"192.168.0.0/22".parse()?,
836    ///         &"192.168.0.0/23".parse()?,
837    ///         &"192.168.0.0/24".parse()?,
838    ///         &"192.168.2.0/23".parse()?,
839    ///         &"192.168.2.0/24".parse()?,
840    ///     ]
841    /// );
842    /// # Ok(())
843    /// # }
844    /// # #[cfg(not(feature = "ipnet"))]
845    /// # fn main() {}
846    /// ```
847    #[inline(always)]
848    pub fn keys(&self) -> Keys<'_, P, T> {
849        Keys { inner: self.iter() }
850    }
851
852    /// Creates a consuming iterator visiting all keys in lexicographic order. The iterator element
853    /// type is `P`.
854    #[inline(always)]
855    pub fn into_keys(self) -> IntoKeys<P, T> {
856        IntoKeys {
857            inner: IntoIter {
858                table: self.table.into_inner(),
859                nodes: vec![0],
860            },
861        }
862    }
863
864    /// An iterator visiting all values in lexicographic order. The iterator element type is `&P`.
865    ///
866    /// ```
867    /// # use prefix_trie::*;
868    /// # #[cfg(feature = "ipnet")]
869    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
870    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
871    /// pm.insert("192.168.0.0/22".parse()?, 1);
872    /// pm.insert("192.168.0.0/23".parse()?, 2);
873    /// pm.insert("192.168.2.0/23".parse()?, 3);
874    /// pm.insert("192.168.0.0/24".parse()?, 4);
875    /// pm.insert("192.168.2.0/24".parse()?, 5);
876    /// assert_eq!(pm.values().collect::<Vec<_>>(), vec![&1, &2, &4, &3, &5]);
877    /// # Ok(())
878    /// # }
879    /// # #[cfg(not(feature = "ipnet"))]
880    /// # fn main() {}
881    /// ```
882    #[inline(always)]
883    pub fn values(&self) -> Values<'_, P, T> {
884        Values { inner: self.iter() }
885    }
886
887    /// Creates a consuming iterator visiting all values in lexicographic order. The iterator
888    /// element type is `P`.
889    #[inline(always)]
890    pub fn into_values(self) -> IntoValues<P, T> {
891        IntoValues {
892            inner: IntoIter {
893                table: self.table.into_inner(),
894                nodes: vec![0],
895            },
896        }
897    }
898
899    /// Get a mutable iterator over all values. The order of this iterator is lexicographic.
900    pub fn values_mut(&mut self) -> ValuesMut<'_, P, T> {
901        ValuesMut {
902            inner: self.iter_mut(),
903        }
904    }
905}
906
907impl<P, T> PrefixMap<P, T>
908where
909    P: Prefix,
910{
911    /// Get an iterator over the node itself and all children. All elements returned have a prefix
912    /// that is contained within `prefix` itself (or are the same). The iterator yields references
913    /// to both keys and values, i.e., type `(&'a P, &'a T)`. The iterator yields elements in
914    /// lexicographic order.
915    ///
916    /// **Note**: Consider using [`crate::AsView::view_at`] as an alternative.
917    ///
918    /// ```
919    /// # use prefix_trie::*;
920    /// # #[cfg(feature = "ipnet")]
921    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
922    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
923    /// pm.insert("192.168.0.0/22".parse()?, 1);
924    /// pm.insert("192.168.0.0/23".parse()?, 2);
925    /// pm.insert("192.168.2.0/23".parse()?, 3);
926    /// pm.insert("192.168.0.0/24".parse()?, 4);
927    /// pm.insert("192.168.2.0/24".parse()?, 5);
928    /// assert_eq!(
929    ///     pm.children(&"192.168.0.0/23".parse()?).collect::<Vec<_>>(),
930    ///     vec![
931    ///         (&"192.168.0.0/23".parse()?, &2),
932    ///         (&"192.168.0.0/24".parse()?, &4),
933    ///     ]
934    /// );
935    /// # Ok(())
936    /// # }
937    /// # #[cfg(not(feature = "ipnet"))]
938    /// # fn main() {}
939    /// ```
940    pub fn children<'a>(&'a self, prefix: &P) -> Iter<'a, P, T> {
941        let nodes = iter::lpm_children_iter_start(&self.table, prefix);
942        Iter {
943            table: Some(&self.table),
944            nodes,
945        }
946    }
947
948    /// Get an iterator of mutable references of the node itself and all its children. All elements
949    /// returned have a prefix that is contained within `prefix` itself (or are the same). The
950    /// iterator yields references to the keys, and mutable references to the values, i.e., type
951    /// `(&'a P, &'a mut T)`. The iterator yields elements in lexicographic order.
952    ///
953    /// **Note**: Consider using [`crate::AsViewMut::view_mut_at`] as an alternative.
954    ///
955    /// ```
956    /// # use prefix_trie::*;
957    /// # #[cfg(feature = "ipnet")]
958    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
959    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
960    /// pm.insert("192.168.0.0/22".parse()?, 1);
961    /// pm.insert("192.168.0.0/23".parse()?, 2);
962    /// pm.insert("192.168.0.0/24".parse()?, 3);
963    /// pm.insert("192.168.2.0/23".parse()?, 4);
964    /// pm.insert("192.168.2.0/24".parse()?, 5);
965    /// pm.children_mut(&"192.168.0.0/23".parse()?).for_each(|(_, x)| *x *= 10);
966    /// assert_eq!(
967    ///     pm.into_iter().collect::<Vec<_>>(),
968    ///     vec![
969    ///         ("192.168.0.0/22".parse()?, 1),
970    ///         ("192.168.0.0/23".parse()?, 20),
971    ///         ("192.168.0.0/24".parse()?, 30),
972    ///         ("192.168.2.0/23".parse()?, 4),
973    ///         ("192.168.2.0/24".parse()?, 5),
974    ///     ]
975    /// );
976    /// # Ok(())
977    /// # }
978    /// # #[cfg(not(feature = "ipnet"))]
979    /// # fn main() {}
980    /// ```
981    pub fn children_mut<'a>(&'a mut self, prefix: &P) -> IterMut<'a, P, T> {
982        let nodes = lpm_children_iter_start(&self.table, prefix);
983        IterMut {
984            table: Some(&self.table),
985            nodes,
986        }
987    }
988
989    /// Get an iterator over the node itself and all children with a value. All elements returned
990    /// have a prefix that is contained within `prefix` itself (or are the same). This function will
991    /// consume `self`, returning an iterator over all owned children.
992    ///
993    /// ```
994    /// # use prefix_trie::*;
995    /// # #[cfg(feature = "ipnet")]
996    /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
997    /// let mut pm: PrefixMap<ipnet::Ipv4Net, _> = PrefixMap::new();
998    /// pm.insert("192.168.0.0/22".parse()?, 1);
999    /// pm.insert("192.168.0.0/23".parse()?, 2);
1000    /// pm.insert("192.168.2.0/23".parse()?, 3);
1001    /// pm.insert("192.168.0.0/24".parse()?, 4);
1002    /// pm.insert("192.168.2.0/24".parse()?, 5);
1003    /// assert_eq!(
1004    ///     pm.into_children(&"192.168.0.0/23".parse()?).collect::<Vec<_>>(),
1005    ///     vec![
1006    ///         ("192.168.0.0/23".parse()?, 2),
1007    ///         ("192.168.0.0/24".parse()?, 4),
1008    ///     ]
1009    /// );
1010    /// # Ok(())
1011    /// # }
1012    /// # #[cfg(not(feature = "ipnet"))]
1013    /// # fn main() {}
1014    /// ```
1015    pub fn into_children(self, prefix: &P) -> IntoIter<P, T> {
1016        let nodes = lpm_children_iter_start(&self.table, prefix);
1017        IntoIter {
1018            table: self.table.into_inner(),
1019            nodes,
1020        }
1021    }
1022}
1023
1024/// Private function implementations
1025impl<P, T> PrefixMap<P, T>
1026where
1027    P: Prefix,
1028{
1029    /// remove all elements from that point onwards.
1030    fn _do_remove_children(&mut self, idx: usize, right: bool) {
1031        let mut to_free = vec![self.table.get_child(idx, right).unwrap()];
1032        self.table.clear_child(idx, right);
1033        while let Some(idx) = to_free.pop() {
1034            let mut dec = 0;
1035            let node = &mut self.table[idx];
1036            let value = node.value.take();
1037            // decrease the count if `value` is something
1038            if value.is_some() {
1039                dec = 1;
1040            }
1041            if let Some(left) = node.left.take() {
1042                to_free.push(left)
1043            }
1044            if let Some(right) = node.right.take() {
1045                to_free.push(right)
1046            }
1047            self.free.push(idx);
1048            self.count -= dec;
1049        }
1050    }
1051
1052    /// insert a new node into the table and return its index. This function also increments the
1053    /// count by 1, but only if `value` is `Some`.
1054    #[inline(always)]
1055    fn new_node(&mut self, prefix: P, value: Option<T>) -> usize {
1056        if value.is_some() {
1057            self.count += 1;
1058        }
1059        if let Some(idx) = self.free.pop() {
1060            let node = &mut self.table[idx];
1061            node.prefix = prefix;
1062            node.value = value;
1063            node.left = None;
1064            node.right = None;
1065            idx
1066        } else {
1067            let table = self.table.as_mut();
1068            let idx = table.len();
1069            table.push(Node {
1070                prefix,
1071                value,
1072                left: None,
1073                right: None,
1074            });
1075            idx
1076        }
1077    }
1078
1079    /// Remove a child from the tree. If the parent was removed, return `true` as a second return parameter
1080    fn _remove_node(
1081        &mut self,
1082        idx: usize,
1083        par: Option<usize>,
1084        par_right: bool,
1085        grp: Option<usize>,
1086        grp_right: bool,
1087    ) -> (Option<T>, bool) {
1088        // if we reach this point, then `idx` is the element to remove, `parent` is its parent,
1089        // and `parent_right` stores the direction of `idx` at `parent`.
1090        let node = &mut self.table[idx];
1091        let value = node.value.take();
1092        let has_left = node.left.is_some();
1093        let has_right = node.right.is_some();
1094
1095        // decrease the number of elements if value is something
1096        if value.is_some() {
1097            self.count -= 1;
1098        }
1099
1100        if has_left && has_right {
1101            // if the node has both left and right set, then it must remain in the tree.
1102        } else if !(has_left || has_right) {
1103            if let Some(par) = par {
1104                // if the node is a leaf, simply remove it.
1105                self.table.clear_child(par, par_right);
1106                self.free.push(idx);
1107                // now, if the parent has no value, also remove the parent and replace it with the
1108                // current node. but only do that if the grandparent is something.
1109                if let Some(grp) = grp {
1110                    if self.table[par].value.is_none() {
1111                        if let Some(sibling) = self.table.get_child(par, !par_right) {
1112                            self.table.set_child(grp, sibling, grp_right);
1113                            return (value, true);
1114                        } else {
1115                            self.table.clear_child(grp, grp_right);
1116                        }
1117                    }
1118                }
1119            }
1120        } else {
1121            // one child remains. simply connect that child directly to the parent if the parent is Something.
1122            if let Some(par) = par {
1123                let child_right = has_right;
1124                let child = self.table.clear_child(idx, child_right).unwrap();
1125                self.table.set_child(par, child, par_right);
1126                self.free.push(idx);
1127            }
1128        }
1129        (value, false)
1130    }
1131
1132    /// recursive retain implementation
1133    pub(crate) fn _retain<F>(
1134        &mut self,
1135        idx: usize,
1136        par: Option<usize>,
1137        par_right: bool,
1138        grp: Option<usize>,
1139        grp_right: bool,
1140        mut f: F,
1141    ) -> (F, bool)
1142    where
1143        F: FnMut(&P, &T) -> bool,
1144    {
1145        // first, do the recursion
1146        let mut idx_removed = false;
1147        let mut par_removed = false;
1148        if let Some(left) = self.table[idx].left {
1149            (f, idx_removed) = self._retain(left, Some(idx), false, par, par_right, f);
1150        }
1151        if let Some(right) = self.table[idx].right {
1152            if idx_removed {
1153                (f, par_removed) = self._retain(right, par, par_right, grp, grp_right, f);
1154            } else {
1155                (f, _) = self._retain(right, Some(idx), true, par, par_right, f);
1156            }
1157        }
1158        // then, check if we need to delete the node
1159        if let Some(val) = self.table[idx].value.as_ref() {
1160            if !f(&self.table[idx].prefix, val) {
1161                // deletion is necessary.
1162                let (_, par_del) = self._remove_node(idx, par, par_right, grp, grp_right);
1163                par_removed = par_del;
1164            }
1165        }
1166        (f, par_removed)
1167    }
1168}
1169
1170impl<P, L, Rhs> PartialEq<Rhs> for PrefixMap<P, L>
1171where
1172    P: Prefix + PartialEq,
1173    L: PartialEq<Rhs::T>,
1174    Rhs: crate::AsView<P = P>,
1175{
1176    fn eq(&self, other: &Rhs) -> bool {
1177        self.iter()
1178            .zip(other.view().iter())
1179            .all(|((lp, lt), (rp, rt))| lt == rt && lp == rp)
1180    }
1181}
1182
1183impl<P, T> Eq for PrefixMap<P, T>
1184where
1185    P: Prefix + Eq,
1186    T: Eq,
1187{
1188}