src/norms.rs

branch
dev
changeset 59
9226980e45a7
parent 33
75d65fa74eba
child 60
848ecc05becf
equal deleted inserted replaced
58:1a38447a89fa 59:9226980e45a7
1 /*! 1 /*!
2 Norms, projections, etc. 2 Norms, projections, etc.
3 */ 3 */
4 4
5 use serde::Serialize; 5 use serde::Serialize;
6 use std::marker::PhantomData;
6 use crate::types::*; 7 use crate::types::*;
7 use crate::euclidean::*; 8 use crate::euclidean::*;
9 use crate::mapping::{Mapping, Space, Instance};
8 10
9 // 11 //
10 // Abstract norms 12 // Abstract norms
11 // 13 //
12 14
15 #[derive(Copy,Clone,Debug)]
16 /// Helper structure to convert a [`NormExponent`] into a [`Mapping`]
17 pub struct NormMapping<F : Float, E : NormExponent>{
18 pub(crate) exponent : E,
19 _phantoms : PhantomData<F>
20 }
21
13 /// An exponent for norms. 22 /// An exponent for norms.
14 /// 23 ///
15 // Just a collection of desirable attributes for a marker type 24 // Just a collection of desirable attributes for a marker type
16 pub trait NormExponent : Copy + Send + Sync + 'static {} 25 pub trait NormExponent : Copy + Send + Sync + 'static {
17 26 /// Return the norm as a mappin
27 fn as_mapping<F : Float>(self) -> NormMapping<F, Self> {
28 NormMapping{ exponent : self, _phantoms : PhantomData }
29 }
30 }
18 31
19 /// Exponent type for the 1-[`Norm`]. 32 /// Exponent type for the 1-[`Norm`].
20 #[derive(Copy,Debug,Clone,Serialize,Eq,PartialEq)] 33 #[derive(Copy,Debug,Clone,Serialize,Eq,PartialEq)]
21 pub struct L1; 34 pub struct L1;
22 impl NormExponent for L1 {} 35 impl NormExponent for L1 {}
34 /// Exponent type for 2,1-[`Norm`]. 47 /// Exponent type for 2,1-[`Norm`].
35 /// (1-norm over a domain Ω, 2-norm of a vector at each point of the domain.) 48 /// (1-norm over a domain Ω, 2-norm of a vector at each point of the domain.)
36 #[derive(Copy,Debug,Clone,Serialize,Eq,PartialEq)] 49 #[derive(Copy,Debug,Clone,Serialize,Eq,PartialEq)]
37 pub struct L21; 50 pub struct L21;
38 impl NormExponent for L21 {} 51 impl NormExponent for L21 {}
52
53 /// Norms for pairs (a, b). ‖(a,b)‖ = ‖(‖a‖_A, ‖b‖_B)‖_J
54 /// For use with [`crate::direct_product::Pair`]
55 #[derive(Copy,Debug,Clone,Serialize,Eq,PartialEq)]
56 pub struct PairNorm<A, B, J>(pub A, pub B, pub J);
57
58 impl<A, B, J> NormExponent for PairNorm<A, B, J>
59 where A : NormExponent, B : NormExponent, J : NormExponent {}
60
39 61
40 /// A Huber/Moreau–Yosida smoothed [`L1`] norm. (Not a norm itself.) 62 /// A Huber/Moreau–Yosida smoothed [`L1`] norm. (Not a norm itself.)
41 /// 63 ///
42 /// The parameter γ of this type is the smoothing factor. Zero means no smoothing, and higher 64 /// The parameter γ of this type is the smoothing factor. Zero means no smoothing, and higher
43 /// values more smoothing. Behaviour with γ < 0 is undefined. 65 /// values more smoothing. Behaviour with γ < 0 is undefined.
152 fn dist(&self, other : &Self, huber : HuberL1<F>) -> F { 174 fn dist(&self, other : &Self, huber : HuberL1<F>) -> F {
153 huber.apply(self.dist2_squared(other)) 175 huber.apply(self.dist2_squared(other))
154 } 176 }
155 } 177 }
156 178
179 impl<F : Float, E : Norm<F, L2>> Norm<F, L21> for Vec<E> {
180 fn norm(&self, _l21 : L21) -> F {
181 self.iter().map(|e| e.norm(L2)).sum()
182 }
183 }
184
185 impl<F : Float, E : Dist<F, L2>> Dist<F, L21> for Vec<E> {
186 fn dist(&self, other : &Self, _l21 : L21) -> F {
187 self.iter().zip(other.iter()).map(|(e, g)| e.dist(g, L2)).sum()
188 }
189 }
190
191 impl<E, F, Domain> Mapping<Domain> for NormMapping<F, E>
192 where
193 F : Float,
194 E : NormExponent,
195 Domain : Space + Norm<F, E>,
196 {
197 type Codomain = F;
198
199 #[inline]
200 fn apply<I : Instance<Domain>>(&self, x : I) -> F {
201 x.eval(|r| r.norm(self.exponent))
202 }
203 }
204

mercurial