From 6a6051032848692c6a2de4b19801bcc3f853ff14 Mon Sep 17 00:00:00 2001 From: ripytide Date: Wed, 23 Nov 2022 17:08:08 +0000 Subject: [PATCH] after a bit not sure what I changed --- range_bounds_set/src/bound_ext.rs | 23 -- range_bounds_set/src/bounds.rs | 205 ++++++++++++++++++ range_bounds_set/src/lib.rs | 8 +- .../{range_bounds_ext.rs => range_bounds.rs} | 31 +-- range_bounds_set/src/range_bounds_set.rs | 64 +++--- range_bounds_set/src/specific_bounds.rs | 85 -------- 6 files changed, 261 insertions(+), 155 deletions(-) delete mode 100644 range_bounds_set/src/bound_ext.rs create mode 100644 range_bounds_set/src/bounds.rs rename range_bounds_set/src/{range_bounds_ext.rs => range_bounds.rs} (59%) delete mode 100644 range_bounds_set/src/specific_bounds.rs diff --git a/range_bounds_set/src/bound_ext.rs b/range_bounds_set/src/bound_ext.rs deleted file mode 100644 index f4f2cf4..0000000 --- a/range_bounds_set/src/bound_ext.rs +++ /dev/null @@ -1,23 +0,0 @@ -use std::ops::Bound; - -pub trait BoundExt { - fn inner(&self) -> Option<&T>; - fn is_unbounded(&self) -> bool; -} - -impl BoundExt for Bound { - fn inner(&self) -> Option<&T> { - match self { - Bound::Included(inner) => Some(inner), - Bound::Excluded(inner) => Some(inner), - Bound::Unbounded => None, - } - } - - fn is_unbounded(&self) -> bool { - match self { - Bound::Unbounded => true, - _ => false, - } - } -} diff --git a/range_bounds_set/src/bounds.rs b/range_bounds_set/src/bounds.rs new file mode 100644 index 0000000..ac8aa9b --- /dev/null +++ b/range_bounds_set/src/bounds.rs @@ -0,0 +1,205 @@ +use std::cmp::Ordering; + +use crate::range_bounds::RangeBounds; + +pub enum StartBound { + Included(T), + Excluded(T), + Unbounded, +} + +impl StartBound { + pub fn inner(&self) -> Option<&T> { + match self { + StartBound::Included(inner) => Some(inner), + StartBound::Excluded(inner) => Some(inner), + StartBound::Unbounded => None, + } + } + + pub fn is_unbounded(&self) -> bool { + match self { + StartBound::Unbounded => true, + _ => false, + } + } + + pub fn copy_outer(&self) -> StartBound<&T> { + match self { + StartBound::Included(ref point) => StartBound::Included(point), + StartBound::Excluded(ref point) => StartBound::Excluded(point), + StartBound::Unbounded => StartBound::Unbounded, + } + } +} +impl StartBound<&T> +where + T: Clone, +{ + pub fn cloned(&self) -> StartBound { + match self { + StartBound::Included(point) => { + StartBound::Included((*point).clone()) + } + StartBound::Excluded(point) => { + StartBound::Excluded((*point).clone()) + } + StartBound::Unbounded => StartBound::Unbounded, + } + } +} + +impl PartialEq for StartBound +where + T: PartialEq, +{ + fn eq(&self, other: &Self) -> bool { + match (self.inner(), other.inner()) { + (Some(start1), Some(start2)) => start1 == start2, + (None, None) => true, + _ => false, + } + } +} + +impl Eq for StartBound where T: PartialEq {} + +impl PartialOrd for StartBound +where + T: PartialOrd, +{ + fn partial_cmp(&self, other: &Self) -> Option { + match (self.inner(), other.inner()) { + //todo fix meh + (Some(start1), Some(start2)) => start1.partial_cmp(start2), + (None, Some(_)) => Some(Ordering::Less), + (Some(_), None) => Some(Ordering::Greater), + (None, None) => Some(Ordering::Equal), + } + } +} + +impl Ord for StartBound +where + T: PartialOrd, +{ + fn cmp(&self, other: &Self) -> Ordering { + self.partial_cmp(other).unwrap() + } +} + +impl From> for StartBound { + fn from(end_bound: EndBound) -> Self { + match end_bound { + EndBound::Included(point) => StartBound::Included(point), + EndBound::Excluded(point) => StartBound::Excluded(point), + EndBound::Unbounded => StartBound::Unbounded, + } + } +} + +pub enum EndBound { + Included(T), + Excluded(T), + Unbounded, +} + +impl EndBound { + pub fn inner(&self) -> Option<&T> { + match self { + EndBound::Included(inner) => Some(inner), + EndBound::Excluded(inner) => Some(inner), + EndBound::Unbounded => None, + } + } + + pub fn is_unbounded(&self) -> bool { + match self { + EndBound::Unbounded => true, + _ => false, + } + } + + pub fn copy_outer(&self) -> EndBound<&T> { + match self { + EndBound::Included(ref point) => EndBound::Included(point), + EndBound::Excluded(ref point) => EndBound::Excluded(point), + EndBound::Unbounded => EndBound::Unbounded, + } + } +} + +impl EndBound<&T> +where + T: Clone, +{ + pub fn cloned(&self) -> EndBound { + match self { + EndBound::Included(point) => EndBound::Included((*point).clone()), + EndBound::Excluded(point) => EndBound::Excluded((*point).clone()), + EndBound::Unbounded => EndBound::Unbounded, + } + } +} + +impl PartialEq for EndBound +where + T: PartialEq, +{ + fn eq(&self, other: &Self) -> bool { + match (self.inner(), other.inner()) { + (Some(start1), Some(start2)) => start1 == start2, + (None, None) => true, + _ => false, + } + } +} + +impl Eq for EndBound where T: PartialEq {} + +impl PartialOrd for EndBound +where + T: PartialOrd, +{ + fn partial_cmp(&self, other: &Self) -> Option { + match (self.inner(), other.inner()) { + //todo fix meh + (Some(start1), Some(start2)) => start1.partial_cmp(start2), + (None, Some(_)) => Some(Ordering::Less), + (Some(_), None) => Some(Ordering::Greater), + (None, None) => Some(Ordering::Equal), + } + } +} + +impl Ord for EndBound +where + T: PartialOrd, +{ + fn cmp(&self, other: &Self) -> Ordering { + self.partial_cmp(other).unwrap() + } +} + +impl From> for EndBound { + fn from(start_bound: StartBound) -> Self { + match start_bound { + StartBound::Included(point) => EndBound::Included(point), + StartBound::Excluded(point) => EndBound::Excluded(point), + StartBound::Unbounded => EndBound::Unbounded, + } + } +} + +impl RangeBounds> + for (StartBound>, EndBound>) +where + T: Ord, +{ + fn start_bound(&self) -> StartBound<&EndBound> { + self.0.copy_outer() + } + fn end_bound(&self) -> EndBound<&EndBound> { + self.1.copy_outer() + } +} diff --git a/range_bounds_set/src/lib.rs b/range_bounds_set/src/lib.rs index 5844b17..9cb213e 100644 --- a/range_bounds_set/src/lib.rs +++ b/range_bounds_set/src/lib.rs @@ -1,5 +1,7 @@ #![feature(is_some_and)] -pub mod bound_ext; -pub mod range_bounds_ext; +pub mod bounds; +pub mod range_bounds; pub mod range_bounds_set; -pub mod specific_bounds; + +pub use std::ops::RangeBounds as StdRangeBounds; +pub use std::ops::Bound as StdBound; diff --git a/range_bounds_set/src/range_bounds_ext.rs b/range_bounds_set/src/range_bounds.rs similarity index 59% rename from range_bounds_set/src/range_bounds_ext.rs rename to range_bounds_set/src/range_bounds.rs index a9b4b0b..02ffa73 100644 --- a/range_bounds_set/src/range_bounds_ext.rs +++ b/range_bounds_set/src/range_bounds.rs @@ -1,20 +1,25 @@ -use std::ops::{Bound, RangeBounds}; +use crate::bounds::{EndBound, StartBound}; -use crate::bound_ext::BoundExt; - -pub trait RangeBoundsExt { - fn overlaps(&self, other: &Self) -> bool; - fn get_pair(&self) -> (Bound<&T>, Bound<&T>); -} - -impl RangeBoundsExt for K +pub trait RangeBounds where - K: RangeBounds, T: PartialOrd, { - fn get_pair(&self) -> (Bound<&T>, Bound<&T>) { + fn start_bound(&self) -> StartBound<&T>; + fn end_bound(&self) -> EndBound<&T>; + fn get_pair(&self) -> (StartBound<&T>, EndBound<&T>) { (self.start_bound(), self.end_bound()) } + fn contains(&self, item: &T) -> bool { + (match self.start_bound() { + StartBound::Included(start) => start <= item, + StartBound::Excluded(start) => start < item, + StartBound::Unbounded => true, + }) && (match self.end_bound() { + EndBound::Included(end) => item <= end, + EndBound::Excluded(end) => item < end, + EndBound::Unbounded => true, + }) + } fn overlaps(&self, other: &Self) -> bool { let self_start_contained = self .start_bound() @@ -38,8 +43,8 @@ where && other.end_bound().is_unbounded(); let same_exclusive = match (self.get_pair(), other.get_pair()) { ( - (Bound::Excluded(start1), Bound::Excluded(end1)), - (Bound::Excluded(start2), Bound::Excluded(end2)), + (StartBound::Excluded(start1), EndBound::Excluded(end1)), + (StartBound::Excluded(start2), EndBound::Excluded(end2)), ) if start1 == start2 && end1 == end2 => true, _ => false, }; diff --git a/range_bounds_set/src/range_bounds_set.rs b/range_bounds_set/src/range_bounds_set.rs index 5bcd913..5466bb6 100644 --- a/range_bounds_set/src/range_bounds_set.rs +++ b/range_bounds_set/src/range_bounds_set.rs @@ -1,23 +1,19 @@ -use std::collections::{BTreeSet, HashMap}; +use std::collections::{BTreeSet, HashMap, BTreeMap}; use std::marker::PhantomData; -use std::ops::{Bound, RangeBounds}; use derive_new::new; -use crate::specific_bounds::{EndBound, StartBound}; +use crate::bounds::{EndBound, StartBound}; +use crate::range_bounds::RangeBounds; +use crate::StdBound; type Id = u128; //todo switch to slot map thingy -#[derive(Default, new)] +#[derive(new)] pub struct RangeBoundsSet { - #[new(default)] - ranges: HashMap, - #[new(default)] - starts: BTreeSet>, - #[new(default)] - ends: BTreeSet>, - phantom_data: PhantomData, + #[new(value="BTreeMap::new()")] + starts: BTreeMap, T>, #[new(default)] id: u128, @@ -30,18 +26,24 @@ where { //returns Err(()) if the inserting the given range overlaps another range //coalesces ranges if they touch - pub fn insert(&mut self, range: T) -> Result<(), ()> { + pub fn insert(&mut self, range_bounds: T) -> Result<(), ()> { Ok(()) } - pub fn raw_insert(&mut self, range: T) {} + pub fn raw_insert(&mut self, range_bounds: T) {} - pub fn overlapping(&self, range: T) { - let end_bounds_range = ( - EndBound::from(range.start_bound().cloned()), - EndBound::from(range.end_bound().cloned()), + pub fn overlapping(&self, range_bounds: T) { + let start_range_bounds = ( + //we require the EndBound:Ord imlementation to work with + //the Included range only + StdBound::Included(range_bounds.start_bound().cloned()), + StdBound::Included(StartBound::from(range_bounds.end_bound().cloned())), ); - self.ends.range(end_bounds_range); + //this range will hold all the ranges we want except possibly + //the last RangeBounds + let ends_range = self.starts.range(start_range_bounds); + + let possible_missing_range_bounds = self.starts. } pub fn get(&self, point: &I) {} @@ -70,17 +72,17 @@ mod tests { // script to streamline the manual input process. The script // essentially enumerates all of the generated cases and asks me // to input the expected - // - // - // - // - // - // - // - // - // - // - // Rusts Bounds types are overly ambiguous in RangeBouns, it - // should return StartBound and EndBound so that you can - // implement Ord on them + // + // + // + // + // + // + // + // + // + // + // Rusts Bounds types are overly ambiguous in RangeBouns, it + // should return StartBound and EndBound so that you can + // implement Ord on them } diff --git a/range_bounds_set/src/specific_bounds.rs b/range_bounds_set/src/specific_bounds.rs deleted file mode 100644 index 0d8299c..0000000 --- a/range_bounds_set/src/specific_bounds.rs +++ /dev/null @@ -1,85 +0,0 @@ -use std::cmp::Ordering; -use std::ops::{Bound, RangeBounds}; - -use crate::bound_ext::BoundExt; - -pub enum EndBound { - Included(T), - Excluded(T), - Unbounded, -} - -impl PartialEq for EndBound -where - T: PartialEq, -{ - fn eq(&self, other: &Self) -> bool { - match (self.inner(), other.inner()) { - (Some(start1), Some(start2)) => start1 == start2, - (None, None) => true, - _ => false, - } - } -} - -impl Eq for EndBound where T: PartialEq {} - -impl PartialOrd for EndBound -where - T: PartialOrd, -{ - fn partial_cmp(&self, other: &Self) -> Option { - match (self.inner(), other.inner()) { - //todo fix meh - (Some(start1), Some(start2)) => start1.partial_cmp(start2), - (None, Some(_)) => Some(Ordering::Less), - (Some(_), None) => Some(Ordering::Greater), - (None, None) => Some(Ordering::Equal), - } - } -} - -impl Ord for EndBound -where - T: PartialOrd, -{ - fn cmp(&self, other: &Self) -> Ordering { - self.partial_cmp(other).unwrap() - } -} - -impl RangeBounds> for (EndBound, EndBound) { - fn start_bound(&self) -> Bound<&EndBound> { - self.0 - } - fn end_bound(&self) -> Bound<&EndBound> { - self.1 - } -} - -impl BoundExt for EndBound { - fn inner(&self) -> Option<&T> { - match self { - EndBound::Included(inner) => Some(inner), - EndBound::Excluded(inner) => Some(inner), - EndBound::Unbounded => None, - } - } - - fn is_unbounded(&self) -> bool { - match self { - EndBound::Unbounded => true, - _ => false, - } - } -} - -impl From> for EndBound { - fn from(value: Bound) -> Self { - match value { - Bound::Included(item) => EndBound::Included(item), - Bound::Excluded(item) => EndBound::Excluded(item), - Bound::Unbounded => Self::Unbounded, - } - } -}