use crate::{constraints::props::{Propagate, Prune}, variables::VarId, variables::views::{Context, View}};
#[derive(Clone, Copy, Debug)]
#[doc(hidden)]
pub struct Add<U, V> {
x: U,
y: V,
s: VarId,
}
impl<U, V> Add<U, V> {
pub const fn new(x: U, y: V, s: VarId) -> Self {
Self { x, y, s }
}
pub const fn x(&self) -> &U {
&self.x
}
pub const fn y(&self) -> &V {
&self.y
}
pub const fn s(&self) -> VarId {
self.s
}
}
impl<U: View, V: View> Prune for Add<U, V> {
fn prune(&self, ctx: &mut Context) -> Option<()> {
let _min = self.s.try_set_min(self.x.min(ctx) + self.y.min(ctx), ctx)?;
let _max = self.s.try_set_max(self.x.max(ctx) + self.y.max(ctx), ctx)?;
let _min = self.x.try_set_min(self.s.min(ctx) - self.y.max(ctx), ctx)?;
let _max = self.x.try_set_max(self.s.max(ctx) - self.y.min(ctx), ctx)?;
let _min = self.y.try_set_min(self.s.min(ctx) - self.x.max(ctx), ctx)?;
let _max = self.y.try_set_max(self.s.max(ctx) - self.x.min(ctx), ctx)?;
Some(())
}
}
impl<U: View, V: View> Propagate for Add<U, V> {
fn list_trigger_vars(&self) -> impl Iterator<Item = VarId> {
core::iter::once(self.s)
.chain(self.x.get_underlying_var())
.chain(self.y.get_underlying_var())
}
}