pub struct RMap { /* private fields */ }
Expand description
A collection that manages disjoint, inclusive ranges [start, end]
.
Implementations§
Source§impl RMap
impl RMap
Sourcepub fn insert(&mut self, value: u64)
pub fn insert(&mut self, value: u64)
Inserts a value into the RMap.
§Behavior
- Create a new range
[value, value]
ifvalue
is isolated. - Extend an existing range if
value
is adjacent to it (e.g., inserting5
into[1, 4]
results in[1, 5]
). - Merge two ranges if
value
bridges them (e.g., inserting3
into a map with[1, 2]
and[4, 5]
results in[1, 5]
). - Do nothing if
value
is already covered by an existing range.
§Complexity
The time complexity is typically O(log N) due to BTreeMap
lookups and insertions,
where N is the number of disjoint ranges in the map. In scenarios involving merges,
a few extra map operations (removals, insertions) might occur, but the overall
complexity remains logarithmic.
§Example
use commonware_storage::rmap::RMap;
let mut map = RMap::new();
map.insert(1); // Map: [1, 1]
assert_eq!(map.next_gap(0), (None, Some(1)));
map.insert(3); // Map: [1, 1], [3, 3]
assert_eq!(map.next_gap(1), (Some(1), Some(3)));
map.insert(2); // Map: [1, 3]
map.insert(0); // Map: [0, 3]
map.insert(5); // Map: [0, 3], [5, 5]
map.insert(4); // Map: [0, 5]
assert_eq!(map.get(&3), Some((0, 5)));
Sourcepub fn get(&self, value: &u64) -> Option<(u64, u64)>
pub fn get(&self, value: &u64) -> Option<(u64, u64)>
Returns the range that contains the given value.
Sourcepub fn remove(&mut self, start: u64, end: u64)
pub fn remove(&mut self, start: u64, end: u64)
Removes a range [start, end]
(inclusive) from the RMap.
§Behavior
- If the removal range completely covers an existing range, the existing range is removed.
- If the removal range is a sub-range of an existing range, the existing range may be split
into two (e.g., removing
[3, 4]
from[1, 6]
results in[1, 2]
and[5, 6]
). - If the removal range overlaps with the start or end of an existing range, the existing
range is truncated (e.g., removing
[1, 2]
from[1, 5]
results in[3, 5]
). - If the removal range covers multiple existing ranges, all such ranges are affected or removed.
- If
start > end
, the method does nothing. - If the removal range does not overlap with any existing range, the map remains unchanged.
§Complexity
The time complexity is O(M + K log N), where N is the total number of ranges in the map, M is the number of ranges that overlap with the removal range (iterate part), and K is the number of new ranges created or ranges removed (at most 2 additions and M removals).
§Example
use commonware_storage::rmap::RMap;
let mut map = RMap::new();
map.insert(1); map.insert(2); map.insert(3); // Map: [1, 3]
map.insert(5); map.insert(6); map.insert(7); // Map: [1, 3], [5, 7]
map.remove(2, 6); // Results in [1, 1], [7, 7]
assert_eq!(map.get(&1), Some((1, 1)));
assert_eq!(map.get(&2), None);
assert_eq!(map.get(&6), None);
assert_eq!(map.get(&7), Some((7, 7)));
Sourcepub fn iter(&self) -> impl Iterator<Item = (&u64, &u64)>
pub fn iter(&self) -> impl Iterator<Item = (&u64, &u64)>
Returns an iterator over the ranges (start, end)
in the RMap.
The ranges are yielded in ascending order of their start points.
Each tuple represents an inclusive range [start, end]
.
§Example
use commonware_storage::rmap::RMap;
let mut map = RMap::new();
map.insert(0); map.insert(1); // Map: [0, 1]
map.insert(3); map.insert(4); // Map: [0, 1], [3, 4]
let mut iter = map.iter();
assert_eq!(iter.next(), Some((&0, &1)));
assert_eq!(iter.next(), Some((&3, &4)));
assert_eq!(iter.next(), None);
Sourcepub fn next_gap(&self, value: u64) -> (Option<u64>, Option<u64>)
pub fn next_gap(&self, value: u64) -> (Option<u64>, Option<u64>)
Finds the end of the range containing value
and the start of the
range succeeding value
. This method is useful for identifying gaps around a given point.
§Behavior
- If
value
falls within an existing range[r_start, r_end]
,current_range_end
will beSome(r_end)
. - If
value
falls in a gap between two ranges[..., prev_end]
and[next_start, ...]
,current_range_end
will beNone
andnext_range_start
will beSome(next_start)
. - If
value
is before all ranges in the map,current_range_end
will beNone
. - If
value
is after all ranges in the map (or within the last range),next_range_start
will beNone
. - If the map is empty, both will be
None
.
§Arguments
value
: Theu64
value to query around.
§Returns
A tuple (Option<u64>, Option<u64>)
where:
- The first element (
current_range_end
) isSome(end)
of the range that containsvalue
. It’sNone
ifvalue
is before all ranges, the map is empty, orvalue
is not in any range. - The second element (
next_range_start
) isSome(start)
of the first range that begins strictly aftervalue
. It’sNone
if no range starts aftervalue
or the map is empty.
§Complexity
O(log N) where N is the number of ranges in RMap.
§Example
use commonware_storage::rmap::RMap;
let mut map = RMap::new();
map.insert(1); map.insert(2); // Map: [1, 2]
map.insert(5); map.insert(6); // Map: [1, 2], [5, 6]
assert_eq!(map.next_gap(0), (None, Some(1))); // Before all ranges
assert_eq!(map.next_gap(1), (Some(2), Some(5))); // Value is at the start of a range
assert_eq!(map.next_gap(2), (Some(2), Some(5))); // Value is at the end of a range
assert_eq!(map.next_gap(3), (None, Some(5))); // Value is in a gap
assert_eq!(map.next_gap(5), (Some(6), None)); // Value is at the start of the last range
assert_eq!(map.next_gap(6), (Some(6), None)); // Value is at the end of the last range
assert_eq!(map.next_gap(7), (None, None)); // After all ranges
Sourcepub fn missing_items(&self, start: u64, max: usize) -> Vec<u64>
pub fn missing_items(&self, start: u64, max: usize) -> Vec<u64>
Returns up to max
missing items starting from start
.
This method iterates through gaps between existing ranges, collecting missing indices
until either max
items are found or there are no more gaps to fill.
§Arguments
start
: The index to start searching from (inclusive).max
: The maximum number of missing items to return.
§Returns
A vector containing up to max
missing indices from gaps between ranges.
The vector may contain fewer than max
items if there aren’t enough gaps.
If there are no more ranges after the current position, no items are returned.
§Complexity
O(G log N + M) where N is the number of ranges in RMap, G is the number of gaps
visited (at most N), and M is the number of missing items returned (at most max
).
Each gap requires a next_gap
call (O(log N)) and collecting items (O(items in gap)).
§Example
use commonware_storage::rmap::RMap;
let mut map = RMap::new();
map.insert(1); map.insert(2); // Map: [1, 2]
map.insert(5); map.insert(6); // Map: [1, 2], [5, 6]
map.insert(10); // Map: [1, 2], [5, 6], [10, 10]
// Starting from 0, find up to 5 missing items
assert_eq!(map.missing_items(0, 5), vec![0, 3, 4, 7, 8]);
// Starting from 3, find up to 3 missing items
assert_eq!(map.missing_items(3, 3), vec![3, 4, 7]);
// Starting from 7, find up to 10 missing items (only gaps are returned)
assert_eq!(map.missing_items(7, 10), vec![7, 8, 9]);
// Starting from 11, there are no more ranges, so no gaps
assert_eq!(map.missing_items(11, 5), Vec::<u64>::new());
Trait Implementations§
impl StructuralPartialEq for RMap
Auto Trait Implementations§
impl Freeze for RMap
impl RefUnwindSafe for RMap
impl Send for RMap
impl Sync for RMap
impl Unpin for RMap
impl UnwindSafe for RMap
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> FutureExt for T
impl<T> FutureExt for T
Source§fn with_context(self, otel_cx: Context) -> WithContext<Self>
fn with_context(self, otel_cx: Context) -> WithContext<Self>
Source§fn with_current_context(self) -> WithContext<Self>
fn with_current_context(self) -> WithContext<Self>
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self
into a Left
variant of Either<Self, Self>
if into_left
is true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self
into a Left
variant of Either<Self, Self>
if into_left(&self)
returns true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read more