mapgraph/map/
mod.rs

1//! Contains traits used as an interface between [`Graph`]s and their backing maps.
2//!
3//! # Map traits
4//!
5//! * [`Map`]: the base trait that should be implemented by any map to be usable with [`Graph`]s.
6//! * [`MapWithCapacity`]: a trait that exposes capacity-related functionality. [`Graph`]s using maps that implement
7//!   this trait as either node or edge maps allow to reserve memory capacity.
8//! * [`OrderedKeyMap`]: a trait for maps that have ordered keys and provide range iterators.
9//! * [`ParIterMap`]: a trait for maps that provide parallel iteration support using [`rayon`].
10//!
11//! ## Insertion traits
12//!
13//! These traits provide interfaces to insert key-value pairs into maps. Usually graphs use maps which generate their
14//! keys internally and expose an opaque key type like [`SlotMap`]. However, the whole point of this library is exposing
15//! the properties of the underlying maps so there is support for maps that accept external keys like [`BTreeMap`].
16//!
17//! * [`IntKeyMap`]: maps that generate their keys internally (e.g. [`SlotMap`]) should implement this trait.
18//! * [`ExtKeyMap`]: maps that allow their users to provide keys (e.g. [`BTreeMap`]) should implement this trait.
19//!
20//! ## Entry API
21//!
22//! Entry API is provided by the [`MapWithEntry`] trait and the [`MapEntry`] type. Implementing this type is mostly
23//! done on their vacant and occupied entry types using the [`VacantMapEntry`] and [`OccupiedMapEntry`] traits.
24//!
25//! [`Graph`]: crate::graph::Graph
26//! [`BTreeMap`]: alloc::collections::BTreeMap
27//! [`SlotMap`]: ::slotmap::SlotMap
28
29#[cfg(feature = "alloc")]
30mod btreemap;
31#[cfg(any(feature = "std", feature = "indexmap"))]
32mod hashmap;
33#[cfg(feature = "slotmap")]
34pub mod slotmap;
35
36use core::{
37    fmt::{self, Debug},
38    ops::RangeBounds,
39};
40#[cfg(feature = "rayon")]
41use rayon::iter::{IntoParallelIterator, Map as ParMap, ParallelIterator};
42
43/// A trait for a generic map that can be used as a node or an edge map in a
44/// [`Graph`](crate::Graph).
45pub trait Map<T>: Default {
46    /// The type of key used by the map.
47    type Key: Copy + Eq + Debug + 'static;
48
49    /// The type for an immutable iterator over the nodes in the map.
50    type Iter<'a>: Iterator<Item = (Self::Key, &'a T)>
51    where
52        Self: 'a,
53        T: 'a;
54
55    /// The type for a mutable iterator over the nodes in the map.
56    type IterMut<'a>: Iterator<Item = (Self::Key, &'a mut T)>
57    where
58        Self: 'a,
59        T: 'a;
60
61    /// Returns the amount of nodes in the map.
62    fn len(&self) -> usize;
63
64    /// Returns `true` if the map is empty.
65    fn is_empty(&self) -> bool {
66        self.len() == 0
67    }
68
69    /// Returns `true` if a map contains the specified key.
70    fn contains_key(&self, index: Self::Key) -> bool {
71        self.get(index).is_some()
72    }
73
74    /// Returns an immutable reference to a value by its key or [`None`] in case the key is
75    /// not present in the map.
76    fn get(&self, index: Self::Key) -> Option<&T>;
77
78    /// Returns a mutable reference to a value by its key or [`None`] in case the key is not
79    /// present in the map.
80    fn get_mut(&mut self, index: Self::Key) -> Option<&mut T>;
81
82    /// Removes a value from a map by its key. Returns the removed value or [`None`] in case the
83    /// key was not present in the map.
84    fn remove(&mut self, index: Self::Key) -> Option<T>;
85
86    /// Removes all the nodes from the map.
87    fn clear(&mut self);
88
89    /// Returns an immutable iterator over the nodes in a map.
90    fn iter(&self) -> Self::Iter<'_>;
91
92    /// Returns a mutable iterator over the nodes in a map.
93    fn iter_mut(&mut self) -> Self::IterMut<'_>;
94}
95
96/// A trait for maps that have some preallocated capacity.
97pub trait MapWithCapacity<T>: Map<T> {
98    /// Allocates a new map with the specified capacity.
99    fn with_capacity(capacity: usize) -> Self;
100
101    /// Returns the currently allocated capacity of the map.
102    fn capacity(&self) -> usize;
103
104    /// Reserves space for at least `additional` nodes.
105    fn reserve(&mut self, additional: usize);
106}
107
108/// An error returned by the [`ExtKeyMap::try_insert`] method when the specified key is already
109/// present in the map.
110#[derive(Debug)]
111pub struct OccupiedError;
112
113impl fmt::Display for OccupiedError {
114    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
115        f.write_str("map entry is occupied")
116    }
117}
118
119#[cfg(feature = "std")]
120impl std::error::Error for OccupiedError {}
121
122/// A trait for maps that accept keys from the caller when adding an entry.
123///
124/// This is what you usually expect when you see something called a "map". Examples are `BTreeMap`,
125/// `HashMap`, etc.
126pub trait ExtKeyMap<T>: Map<T> {
127    /// Tries to insert a key-value pair into the map.
128    ///
129    /// # Errors
130    ///
131    /// In case the key is already present, returns [`OccupiedError`].
132    fn try_insert(&mut self, key: Self::Key, value: T) -> Result<(), OccupiedError>;
133
134    /// Inserts a key-value pair into the map replacing the old value in case the key was present.
135    /// The old value is returned in that case.
136    fn replace(&mut self, key: Self::Key, value: T) -> Option<T>;
137}
138
139/// A trait for maps that produce keys internally when adding an entry.
140///
141/// This is the kind of maps usually used to back graphs in rust. Examples are `SlotMap` and `Slab`.
142pub trait IntKeyMap<T>: Map<T> {
143    /// Inserts a value into the map and returns the key allocated for it.
144    fn insert(&mut self, value: T) -> Self::Key;
145
146    /// Inserts a value produced by a closure into the map and returns the key allocated for it.
147    ///
148    /// The closure receives the allocated key as its only argument.
149    fn insert_with_key<F: FnOnce(Self::Key) -> T>(&mut self, f: F) -> Self::Key;
150}
151
152/// A trait for maps that have strongly ordered keys and provide iterators over key ranges.
153///
154/// The most notable example of such a map is the `BTreeMap`.
155pub trait OrderedKeyMap<T>: ExtKeyMap<T>
156where
157    Self::Key: Ord,
158{
159    /// The type for an immutable range iterator for the map.
160    type Range<'a>: Iterator<Item = (Self::Key, &'a T)> + DoubleEndedIterator
161    where
162        Self: 'a,
163        T: 'a;
164
165    /// The type for a mutable range iterator for the map.
166    type RangeMut<'a>: Iterator<Item = (Self::Key, &'a mut T)> + DoubleEndedIterator
167    where
168        Self: 'a,
169        T: 'a;
170
171    /// Returns an immutable iterator over entries corresponding to keys in the specified range.
172    fn range<R: RangeBounds<Self::Key>>(&self, range: R) -> Self::Range<'_>;
173
174    /// Returns a mutable iterator over entries corresponding to keys in the specified range.
175    fn range_mut<R: RangeBounds<Self::Key>>(&mut self, range: R) -> Self::RangeMut<'_>;
176
177    /// Returns an immutable reference to the first element in the map.
178    ///
179    /// # Default behavior
180    ///
181    /// The default implementation takes the first element returned by the range iterator on an
182    /// unbounded range.
183    fn first(&self) -> Option<(Self::Key, &T)> {
184        self.range(..).next()
185    }
186
187    /// Returns a mutable reference to the first element in the map.
188    ///
189    /// # Default behavior
190    ///
191    /// The default implementation takes the first element returned by the range iterator on an
192    /// unbounded range.
193    fn first_mut(&mut self) -> Option<(Self::Key, &mut T)> {
194        self.range_mut(..).next()
195    }
196
197    /// Returns an immutable reference to the last element in the map.
198    ///
199    /// # Default behavior
200    ///
201    /// The default implementation takes the last element returned by the range iterator on an
202    /// unbounded range.
203    fn last(&self) -> Option<(Self::Key, &T)> {
204        self.range(..).last()
205    }
206
207    /// Returns a mutable reference to the last element in the map.
208    ///
209    /// # Default behavior
210    ///
211    /// The default implementation takes the last element returned by the range iterator on an
212    /// unbounded range.
213    fn last_mut(&mut self) -> Option<(Self::Key, &mut T)> {
214        self.range_mut(..).last()
215    }
216}
217
218/// A trait for maps that provide parallel iterators.
219#[cfg(feature = "rayon")]
220pub trait ParIterMap<T>: Map<T> {
221    /// The type for the map's immutable parallel iterator.
222    type ParIter<'a>: ParallelIterator<Item = (Self::Key, &'a T)>
223    where
224        Self: 'a,
225        T: 'a;
226
227    /// The type for the map's mutable parallel iterator.
228    type ParIterMut<'a>: ParallelIterator<Item = (Self::Key, &'a mut T)>
229    where
230        Self: 'a,
231        T: 'a;
232
233    /// Returns an immutable parallel iterator over the key-value pairs in the map.
234    fn par_iter(&self) -> Self::ParIter<'_>;
235
236    /// Returns a mutable parallel iterator over the key-value pairs in the map.
237    fn par_iter_mut(&mut self) -> Self::ParIterMut<'_>;
238}
239
240#[cfg(feature = "rayon")]
241impl<M, K, T> ParIterMap<T> for M
242where
243    M: Map<T, Key = K>,
244    K: Copy + Eq + Debug + Send + Sync + 'static,
245    T: Send + Sync,
246    for<'a> &'a M: IntoParallelIterator<Item = (&'a K, &'a T)>,
247    for<'a> &'a mut M: IntoParallelIterator<Item = (&'a K, &'a mut T)>,
248{
249    type ParIter<'a> = ParMap<
250        <&'a M as IntoParallelIterator>::Iter,
251        fn((&'a K, &'a T)) -> (K, &'a T)
252    > where Self: 'a, T: 'a;
253    type ParIterMut<'a> = ParMap<
254        <&'a mut M as IntoParallelIterator>::Iter,
255        fn((&'a K, &'a mut T)) -> (K, &'a mut T)
256    > where Self: 'a, T: 'a;
257
258    fn par_iter(&self) -> Self::ParIter<'_> {
259        IntoParallelIterator::into_par_iter(self).map(|(&k, v)| (k, v))
260    }
261
262    fn par_iter_mut(&mut self) -> Self::ParIterMut<'_> {
263        IntoParallelIterator::into_par_iter(self).map(|(&k, v)| (k, v))
264    }
265}
266
267/// A set of keys.
268///
269/// This is used to mark keys that have already been visited in algorithms.
270///
271/// Implementing this using a separate trait instead of relying on the [`ExtKeyMap`] trait allows to
272/// use simpler set structures like bit sets with less friction.
273///
274/// # Auto trait implementations
275///
276/// All types that implement [`ExtKeyMap<()>`] automatically implement this trait.
277pub trait KeySet<K: Copy + Eq + Debug + 'static> {
278    /// Returns the amount of keys in the set.
279    fn len(&self) -> usize;
280
281    /// Returns `true` if the set is empty.
282    fn is_empty(&self) -> bool {
283        self.len() == 0
284    }
285
286    /// Returns `true` if a set contains the specified key.
287    fn contains(&self, index: K) -> bool;
288
289    /// Inserts a key into the set.
290    ///
291    /// Returns `true` if the value was not present in the set.
292    fn insert(&mut self, index: K) -> bool;
293
294    /// Removes a key from the set.
295    ///
296    /// Returns `true` if the value was present in the set.
297    fn remove(&mut self, index: K) -> bool;
298
299    /// Removes all the nodes from the map.
300    fn clear(&mut self);
301}
302
303impl<K: Copy + Eq + Debug + 'static, T: ExtKeyMap<(), Key = K>> KeySet<K> for T {
304    fn len(&self) -> usize {
305        Map::len(self)
306    }
307
308    fn is_empty(&self) -> bool {
309        Map::is_empty(self)
310    }
311
312    fn contains(&self, index: K) -> bool {
313        Map::contains_key(self, index)
314    }
315
316    fn insert(&mut self, index: K) -> bool {
317        ExtKeyMap::replace(self, index, ()).is_some()
318    }
319
320    fn remove(&mut self, index: K) -> bool {
321        Map::remove(self, index).is_some()
322    }
323
324    fn clear(&mut self) {
325        Map::clear(self)
326    }
327}
328
329/// A trait for vacant map entry types.
330pub trait VacantMapEntry {
331    /// The map's value type.
332    type Value;
333
334    /// Consumes the vacant entry and inserts a value for the corresponding key into the map.
335    fn insert<'a>(self, value: Self::Value) -> &'a mut Self::Value
336    where
337        Self: 'a;
338}
339
340/// A trait for occupied map entry types.
341pub trait OccupiedMapEntry {
342    /// The map's value type.
343    type Value;
344
345    /// Gets an immutable reference to the value stored by the entry.
346    fn get(&self) -> &Self::Value;
347
348    /// Gets a mutable reference to the value stored by the entry.
349    fn get_mut(&mut self) -> &mut Self::Value;
350
351    /// Converts the map entry into a mutable reference to the stored value with a lifetime of the map itself.
352    fn into_mut<'a>(self) -> &'a mut Self::Value
353    where
354        Self: 'a;
355
356    /// Replaces the value stored in the entry with another value and returns the old one.
357    fn replace(&mut self, value: Self::Value) -> Self::Value;
358
359    /// Removes a value from the entry.
360    fn remove(self) -> Self::Value;
361}
362
363/// An enumeration of possible map entry types.
364#[derive(Clone, Debug)]
365pub enum MapEntry<O, V> {
366    /// A vacant map entry.
367    Vacant(V),
368    /// An occupied map entry.
369    Occupied(O),
370}
371
372/// A trait for maps that implement entry API.
373pub trait MapWithEntry<T>: ExtKeyMap<T> {
374    /// The type for the vacant entry.
375    type VacantEntry<'a>: VacantMapEntry<Value = T>
376    where
377        Self: 'a;
378
379    /// The type for the occupied entry.
380    type OccupiedEntry<'a>: OccupiedMapEntry<Value = T>
381    where
382        Self: 'a;
383
384    /// Returns an entry for a key. The entry is either occupied or vacant.
385    fn entry(&mut self, key: Self::Key)
386        -> MapEntry<Self::OccupiedEntry<'_>, Self::VacantEntry<'_>>;
387}