src/bisection_tree/support.rs

branch
dev
changeset 68
c5f70e767511
parent 59
9226980e45a7
child 75
e9f4550cfa18
child 80
f802ddbabcfc
equal deleted inserted replaced
67:d7c0f431cbd6 68:c5f70e767511
11 }; 11 };
12 use crate::sets::Cube; 12 use crate::sets::Cube;
13 use crate::loc::Loc; 13 use crate::loc::Loc;
14 use super::aggregator::Bounds; 14 use super::aggregator::Bounds;
15 use crate::norms::{Norm, L1, L2, Linfinity}; 15 use crate::norms::{Norm, L1, L2, Linfinity};
16 16 pub use crate::operator_arithmetic::{Weighted, Constant};
17 /// A trait for encoding constant [`Float`] values
18 pub trait Constant : Copy + Sync + Send + 'static + std::fmt::Debug + Into<Self::Type> {
19 /// The type of the value
20 type Type : Float;
21 /// Returns the value of the constant
22 fn value(&self) -> Self::Type;
23 }
24
25 impl<F : Float> Constant for F {
26 type Type = F;
27 #[inline]
28 fn value(&self) -> F { *self }
29 }
30
31 17
32 /// A trait for working with the supports of [`Apply`]s. 18 /// A trait for working with the supports of [`Apply`]s.
33 /// 19 ///
34 /// Apply is not a super-trait to allow more general use. 20 /// Apply is not a super-trait to allow more general use.
35 pub trait Support<F : Num, const N : usize> : Sized + Sync + Send + 'static { 21 pub trait Support<F : Num, const N : usize> : Sized + Sync + Send + 'static {
61 47
62 /// Translate `self` by `x`. 48 /// Translate `self` by `x`.
63 #[inline] 49 #[inline]
64 fn shift(self, x : Loc<F, N>) -> Shift<Self, F, N> { 50 fn shift(self, x : Loc<F, N>) -> Shift<Self, F, N> {
65 Shift { shift : x, base_fn : self } 51 Shift { shift : x, base_fn : self }
66 }
67
68 /// Multiply `self` by the scalar `a`.
69 #[inline]
70 fn weigh<C : Constant<Type=F>>(self, a : C) -> Weighted<Self, C> {
71 Weighted { weight : a, base_fn : self }
72 } 52 }
73 } 53 }
74 54
75 /// Trait for globally analysing a property `A` of a [`Apply`]. 55 /// Trait for globally analysing a property `A` of a [`Apply`].
76 /// 56 ///
201 } 181 }
202 )* } 182 )* }
203 } 183 }
204 184
205 impl_shift_norm!(L1 L2 Linfinity); 185 impl_shift_norm!(L1 L2 Linfinity);
206
207 /// Weighting of a [`Support`] and [`Apply`] by scalar multiplication;
208 /// output of [`Support::weigh`].
209 #[derive(Copy,Clone,Debug,Serialize)]
210 pub struct Weighted<T, C : Constant> {
211 /// The weight
212 pub weight : C,
213 /// The base [`Support`] or [`Apply`] being weighted.
214 pub base_fn : T,
215 }
216
217 impl<'a, T, V, F : Float, C, const N : usize> Mapping<Loc<F, N>> for Weighted<T, C>
218 where T : Mapping<Loc<F, N>, Codomain=V>,
219 V : Space + std::ops::Mul<F,Output=V>,
220 C : Constant<Type=F> {
221 type Codomain = V;
222
223 #[inline]
224 fn apply<I : Instance<Loc<F, N>>>(&self, x : I) -> Self::Codomain {
225 self.base_fn.apply(x) * self.weight.value()
226 }
227 }
228
229 impl<'a, T, V, F : Float, C, const N : usize> DifferentiableImpl<Loc<F, N>> for Weighted<T, C>
230 where T : DifferentiableMapping<Loc<F, N>, DerivativeDomain=V>,
231 V : Space + std::ops::Mul<F, Output=V>,
232 C : Constant<Type=F> {
233 type Derivative = V;
234
235 #[inline]
236 fn differential_impl<I : Instance<Loc<F, N>>>(&self, x : I) -> Self::Derivative {
237 self.base_fn.differential(x) * self.weight.value()
238 }
239 }
240 186
241 impl<'a, T, F : Float, C, const N : usize> Support<F,N> for Weighted<T, C> 187 impl<'a, T, F : Float, C, const N : usize> Support<F,N> for Weighted<T, C>
242 where T : Support<F, N>, 188 where T : Support<F, N>,
243 C : Constant<Type=F> { 189 C : Constant<Type=F> {
244 190

mercurial