From f0aa3878c4ab15f4280bb3af98ddc0a1e1dfa603 Mon Sep 17 00:00:00 2001 From: timofey Date: Fri, 16 Jun 2023 08:00:18 +0000 Subject: [PATCH] `flow::binary::bounds` --- src/flow/binary.rs | 1 + src/flow/binary/bounds.rs | 82 +++++++++++++++++++++++++++++ src/rstd/collections/avl/bounds.rs | 83 +----------------------------- 3 files changed, 84 insertions(+), 82 deletions(-) create mode 100644 src/flow/binary/bounds.rs diff --git a/src/flow/binary.rs b/src/flow/binary.rs index 7ce3ac5..adde5ff 100644 --- a/src/flow/binary.rs +++ b/src/flow/binary.rs @@ -1,4 +1,5 @@ mod avl; +pub mod bounds; use crate::flow::comparator::*; use crate::func::{context::*, *}; diff --git a/src/flow/binary/bounds.rs b/src/flow/binary/bounds.rs new file mode 100644 index 0000000..304f884 --- /dev/null +++ b/src/flow/binary/bounds.rs @@ -0,0 +1,82 @@ +use crate::flow::comparator::*; + +#[derive(Clone)] +pub struct Bounds { + l: Option, + r: Option, +} + +pub enum BoundsError { + BoundsViolated { l: A, r: A }, + CannotJoin(A), +} + +impl Bounds { + pub fn unbound() -> Self { + Bounds { l: None, r: None } + } + + fn ordered(l: &A, r: &A, comparator: &impl Comparator) -> Result<(), BoundsError> { + if let Comparison::R = comparator.pick_smaller(l, r) { + Err(BoundsError::BoundsViolated { + l: l.clone(), + r: r.clone(), + }) + } else { + Ok(()) + } + } + + fn new( + l: Option, + r: Option, + comparator: &impl Comparator, + ) -> Result> { + if let (Some(kl), Some(kr)) = (&l, &r) { + Self::ordered(kl, kr, comparator)? + } + Ok(Bounds { l, r }) + } + + pub fn split( + self, + key: &A, + comparator: &impl Comparator, + ) -> Result<(Self, Self), BoundsError> { + Ok(( + Self::new(self.l, Some(key.clone()), comparator)?, + Self::new(Some(key.clone()), self.r, comparator)?, + )) + } + + pub fn join( + l: Self, + r: Self, + key: &A, + comparator: &impl Comparator, + ) -> Result> { + if let Some(lr) = &l.r { + Self::ordered(lr, key, comparator)? + } else { + Err(BoundsError::CannotJoin(key.clone()))? + } + if let Some(rl) = &r.l { + Self::ordered(key, rl, comparator)? + } else { + Err(BoundsError::CannotJoin(key.clone()))? + } + Self::new(l.l, r.r, comparator) + } + + pub fn equal_bound(l: &Option, r: &Option, comparator: &impl Comparator) -> bool { + match (l, r) { + (None, None) => true, + (Some(kl), Some(kr)) => matches!(comparator.pick_smaller(kl, kr), Comparison::E), + _ => false, + } + } + + pub fn equal(bl: &Self, br: &Self, comparator: &impl Comparator) -> bool { + Self::equal_bound(&bl.l, &br.l, comparator) && Self::equal_bound(&bl.r, &br.r, comparator) + } +} diff --git a/src/rstd/collections/avl/bounds.rs b/src/rstd/collections/avl/bounds.rs index 1376f04..341b11c 100644 --- a/src/rstd/collections/avl/bounds.rs +++ b/src/rstd/collections/avl/bounds.rs @@ -1,19 +1,8 @@ -use crate::flow::comparator::*; +use crate::flow::{binary::bounds::*, comparator::*}; use crate::func::context::*; use super::{binary::*, *}; -#[derive(Clone)] -struct Bounds { - l: Option, - r: Option, -} - -pub enum BoundsError { - BoundsViolated { l: A, r: A }, - CannotJoin(A), -} - pub enum BoundError { Avl(AvlError), Bounds(BoundsError), @@ -56,76 +45,6 @@ pub struct BoundReference<'a, Ctx: Context<'a>, A: Mentionable<'a, Ctx>> { bounds: Bounds, } -impl Bounds { - fn unbound() -> Self { - Bounds { l: None, r: None } - } - - fn ordered(l: &A, r: &A, comparator: &impl Comparator) -> Result<(), BoundsError> { - if let Comparison::R = comparator.pick_smaller(l, r) { - Err(BoundsError::BoundsViolated { - l: l.clone(), - r: r.clone(), - }) - } else { - Ok(()) - } - } - - fn new( - l: Option, - r: Option, - comparator: &impl Comparator, - ) -> Result> { - if let (Some(kl), Some(kr)) = (&l, &r) { - Self::ordered(kl, kr, comparator)? - } - Ok(Bounds { l, r }) - } - - fn split( - self, - key: &A, - comparator: &impl Comparator, - ) -> Result<(Self, Self), BoundsError> { - Ok(( - Self::new(self.l, Some(key.clone()), comparator)?, - Self::new(Some(key.clone()), self.r, comparator)?, - )) - } - - fn join( - l: Self, - r: Self, - key: &A, - comparator: &impl Comparator, - ) -> Result> { - if let Some(lr) = &l.r { - Self::ordered(lr, key, comparator)? - } else { - Err(BoundsError::CannotJoin(key.clone()))? - } - if let Some(rl) = &r.l { - Self::ordered(key, rl, comparator)? - } else { - Err(BoundsError::CannotJoin(key.clone()))? - } - Self::new(l.l, r.r, comparator) - } - - pub fn equal_bound(l: &Option, r: &Option, comparator: &impl Comparator) -> bool { - match (l, r) { - (None, None) => true, - (Some(kl), Some(kr)) => matches!(comparator.pick_smaller(kl, kr), Comparison::E), - _ => false, - } - } - - pub fn equal(bl: &Self, br: &Self, comparator: &impl Comparator) -> bool { - Self::equal_bound(&bl.l, &br.l, comparator) && Self::equal_bound(&bl.r, &br.r, comparator) - } -} - pub type BoundSplit<'a, Ctx, A> = (BoundTree<'a, Ctx, A>, BoundTree<'a, Ctx, A>, A); impl<'a, Ctx: Context<'a>, A: Mentionable<'a, Ctx> + Clone> BoundNode<'a, Ctx, A> {