Thu, 29 Aug 2024 00:00:00 -0500
Radon FB + sliding improvements
24
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
1 | /*! |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
2 | Regularisation terms |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
3 | */ |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
4 | |
32 | 5 | use numeric_literals::replace_float_literals; |
24
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
6 | use serde::{Serialize, Deserialize}; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
7 | use alg_tools::norms::Norm; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
8 | use alg_tools::linops::Apply; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
9 | use alg_tools::loc::Loc; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
10 | use crate::types::*; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
11 | use crate::measures::{ |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
12 | DiscreteMeasure, |
32 | 13 | DeltaMeasure, |
24
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
14 | Radon |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
15 | }; |
32 | 16 | use crate::fb::FBGenericConfig; |
24
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
17 | #[allow(unused_imports)] // Used by documentation. |
32 | 18 | use crate::fb::pointsource_fb_reg; |
19 | #[allow(unused_imports)] // Used by documentation. | |
20 | use crate::sliding_fb::pointsource_sliding_fb_reg; | |
24
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
21 | |
32 | 22 | use nalgebra::{DVector, DMatrix}; |
23 | use alg_tools::nalgebra_support::ToNalgebraRealField; | |
24 | use alg_tools::mapping::Mapping; | |
25 | use alg_tools::bisection_tree::{ | |
26 | BTFN, | |
27 | Bounds, | |
28 | BTSearch, | |
29 | P2Minimise, | |
30 | SupportGenerator, | |
31 | LocalAnalysis, | |
32 | Bounded, | |
33 | }; | |
34 | use crate::subproblem::{ | |
35 | nonneg::quadratic_nonneg, | |
36 | unconstrained::quadratic_unconstrained, | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
37 | l1squared_unconstrained::l1squared_unconstrained, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
38 | l1squared_nonneg::l1squared_nonneg |
32 | 39 | }; |
40 | use alg_tools::iterate::AlgIteratorFactory; | |
41 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
42 | use std::cmp::Ordering::{Greater, Less, Equal}; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
43 | |
32 | 44 | /// The regularisation term $α\\|μ\\|\_{ℳ(Ω)} + δ_{≥ 0}(μ)$ for [`pointsource_fb_reg`] and other |
45 | /// algorithms. | |
24
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
46 | /// |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
47 | /// The only member of the struct is the regularisation parameter α. |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
48 | #[derive(Copy, Clone, Debug, Serialize, Deserialize)] |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
49 | pub struct NonnegRadonRegTerm<F : Float>(pub F /* α */); |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
50 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
51 | impl<'a, F : Float> NonnegRadonRegTerm<F> { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
52 | /// Returns the regularisation parameter |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
53 | pub fn α(&self) -> F { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
54 | let &NonnegRadonRegTerm(α) = self; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
55 | α |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
56 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
57 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
58 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
59 | impl<'a, F : Float, const N : usize> Apply<&'a DiscreteMeasure<Loc<F, N>, F>> |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
60 | for NonnegRadonRegTerm<F> { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
61 | type Output = F; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
62 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
63 | fn apply(&self, μ : &'a DiscreteMeasure<Loc<F, N>, F>) -> F { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
64 | self.α() * μ.norm(Radon) |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
65 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
66 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
67 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
68 | |
32 | 69 | /// The regularisation term $α\|μ\|_{ℳ(Ω)}$ for [`pointsource_fb_reg`]. |
24
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
70 | /// |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
71 | /// The only member of the struct is the regularisation parameter α. |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
72 | #[derive(Copy, Clone, Debug, Serialize, Deserialize)] |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
73 | pub struct RadonRegTerm<F : Float>(pub F /* α */); |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
74 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
75 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
76 | impl<'a, F : Float> RadonRegTerm<F> { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
77 | /// Returns the regularisation parameter |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
78 | pub fn α(&self) -> F { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
79 | let &RadonRegTerm(α) = self; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
80 | α |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
81 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
82 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
83 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
84 | impl<'a, F : Float, const N : usize> Apply<&'a DiscreteMeasure<Loc<F, N>, F>> |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
85 | for RadonRegTerm<F> { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
86 | type Output = F; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
87 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
88 | fn apply(&self, μ : &'a DiscreteMeasure<Loc<F, N>, F>) -> F { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
89 | self.α() * μ.norm(Radon) |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
90 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
91 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
92 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
93 | /// Regularisation term configuration |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
94 | #[derive(Clone, Copy, Eq, PartialEq, Serialize, Deserialize, Debug)] |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
95 | pub enum Regularisation<F : Float> { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
96 | /// $α \\|μ\\|\_{ℳ(Ω)}$ |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
97 | Radon(F), |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
98 | /// $α\\|μ\\|\_{ℳ(Ω)} + δ_{≥ 0}(μ)$ |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
99 | NonnegRadon(F), |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
100 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
101 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
102 | impl<'a, F : Float, const N : usize> Apply<&'a DiscreteMeasure<Loc<F, N>, F>> |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
103 | for Regularisation<F> { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
104 | type Output = F; |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
105 | |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
106 | fn apply(&self, μ : &'a DiscreteMeasure<Loc<F, N>, F>) -> F { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
107 | match *self { |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
108 | Self::Radon(α) => RadonRegTerm(α).apply(μ), |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
109 | Self::NonnegRadon(α) => NonnegRadonRegTerm(α).apply(μ), |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
110 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
111 | } |
d29d1fcf5423
Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff
changeset
|
112 | } |
32 | 113 | |
114 | /// Abstraction of regularisation terms for [`generic_pointsource_fb_reg`]. | |
115 | pub trait RegTerm<F : Float + ToNalgebraRealField, const N : usize> | |
116 | : for<'a> Apply<&'a DiscreteMeasure<Loc<F, N>, F>, Output = F> { | |
117 | /// Approximately solve the problem | |
118 | /// <div>$$ | |
119 | /// \min_{x ∈ ℝ^n} \frac{1}{2} x^⊤Ax - g^⊤ x + τ G(x) | |
120 | /// $$</div> | |
121 | /// for $G$ depending on the trait implementation. | |
122 | /// | |
123 | /// The parameter `mA` is $A$. An estimate for its opeator norm should be provided in | |
124 | /// `mA_normest`. The initial iterate and output is `x`. The current main tolerance is `ε`. | |
125 | /// | |
126 | /// Returns the number of iterations taken. | |
127 | fn solve_findim( | |
128 | &self, | |
129 | mA : &DMatrix<F::MixedType>, | |
130 | g : &DVector<F::MixedType>, | |
131 | τ : F, | |
132 | x : &mut DVector<F::MixedType>, | |
133 | mA_normest : F, | |
134 | ε : F, | |
135 | config : &FBGenericConfig<F> | |
136 | ) -> usize; | |
137 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
138 | /// Approximately solve the problem |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
139 | /// <div>$$ |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
140 | /// \min_{x ∈ ℝ^n} \frac{1}{2} |x-y|_1^2 - g^⊤ x + τ G(x) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
141 | /// $$</div> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
142 | /// for $G$ depending on the trait implementation. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
143 | /// |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
144 | /// Returns the number of iterations taken. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
145 | fn solve_findim_l1squared( |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
146 | &self, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
147 | y : &DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
148 | g : &DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
149 | τ : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
150 | x : &mut DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
151 | ε : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
152 | config : &FBGenericConfig<F> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
153 | ) -> usize; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
154 | |
32 | 155 | /// Find a point where `d` may violate the tolerance `ε`. |
156 | /// | |
157 | /// If `skip_by_rough_check` is set, do not find the point if a rough check indicates that we | |
158 | /// are in bounds. `ε` is the current main tolerance and `τ` a scaling factor for the | |
159 | /// regulariser. | |
160 | /// | |
161 | /// Returns `None` if `d` is in bounds either based on the rough check, or a more precise check | |
162 | /// terminating early. Otherwise returns a possibly violating point, the value of `d` there, | |
163 | /// and a boolean indicating whether the found point is in bounds. | |
164 | fn find_tolerance_violation<G, BT>( | |
165 | &self, | |
166 | d : &mut BTFN<F, G, BT, N>, | |
167 | τ : F, | |
168 | ε : F, | |
169 | skip_by_rough_check : bool, | |
170 | config : &FBGenericConfig<F>, | |
171 | ) -> Option<(Loc<F, N>, F, bool)> | |
172 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
173 | G : SupportGenerator<F, N, Id=BT::Data>, | |
174 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
175 | + LocalAnalysis<F, Bounds<F>, N> { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
176 | self.find_tolerance_violation_slack(d, τ, ε, skip_by_rough_check, config, F::ZERO) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
177 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
178 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
179 | /// Find a point where `d` may violate the tolerance `ε`. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
180 | /// |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
181 | /// This version includes a `slack` parameter to expand the tolerances. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
182 | /// It is used for Radon-norm squared proximal term in [`crate::radon_fb`]. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
183 | /// |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
184 | /// If `skip_by_rough_check` is set, do not find the point if a rough check indicates that we |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
185 | /// are in bounds. `ε` is the current main tolerance and `τ` a scaling factor for the |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
186 | /// regulariser. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
187 | /// |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
188 | /// Returns `None` if `d` is in bounds either based on the rough check, or a more precise check |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
189 | /// terminating early. Otherwise returns a possibly violating point, the value of `d` there, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
190 | /// and a boolean indicating whether the found point is in bounds. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
191 | fn find_tolerance_violation_slack<G, BT>( |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
192 | &self, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
193 | d : &mut BTFN<F, G, BT, N>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
194 | τ : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
195 | ε : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
196 | skip_by_rough_check : bool, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
197 | config : &FBGenericConfig<F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
198 | slack : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
199 | ) -> Option<(Loc<F, N>, F, bool)> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
200 | where BT : BTSearch<F, N, Agg=Bounds<F>>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
201 | G : SupportGenerator<F, N, Id=BT::Data>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
202 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> |
32 | 203 | + LocalAnalysis<F, Bounds<F>, N>; |
204 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
205 | |
32 | 206 | /// Verify that `d` is in bounds `ε` for a merge candidate `μ` |
207 | /// | |
208 | /// `ε` is the current main tolerance and `τ` a scaling factor for the regulariser. | |
209 | fn verify_merge_candidate<G, BT>( | |
210 | &self, | |
211 | d : &mut BTFN<F, G, BT, N>, | |
212 | μ : &DiscreteMeasure<Loc<F, N>, F>, | |
213 | τ : F, | |
214 | ε : F, | |
215 | config : &FBGenericConfig<F>, | |
216 | ) -> bool | |
217 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
218 | G : SupportGenerator<F, N, Id=BT::Data>, | |
219 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
220 | + LocalAnalysis<F, Bounds<F>, N>; | |
221 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
222 | /// Verify that `d` is in bounds `ε` for a merge candidate `μ` |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
223 | /// |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
224 | /// This version is s used for Radon-norm squared proximal term in [`crate::radon_fb`]. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
225 | /// The [`DiscreteMeasure`]s `μ` and `radon_μ` are supposed to have same coordinates at |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
226 | /// same agreeing indices. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
227 | /// |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
228 | /// `ε` is the current main tolerance and `τ` a scaling factor for the regulariser. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
229 | fn verify_merge_candidate_radonsq<G, BT>( |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
230 | &self, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
231 | d : &mut BTFN<F, G, BT, N>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
232 | μ : &DiscreteMeasure<Loc<F, N>, F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
233 | τ : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
234 | ε : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
235 | config : &FBGenericConfig<F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
236 | radon_μ :&DiscreteMeasure<Loc<F, N>, F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
237 | ) -> bool |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
238 | where BT : BTSearch<F, N, Agg=Bounds<F>>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
239 | G : SupportGenerator<F, N, Id=BT::Data>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
240 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
241 | + LocalAnalysis<F, Bounds<F>, N>; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
242 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
243 | |
32 | 244 | /// TODO: document this |
245 | fn target_bounds(&self, τ : F, ε : F) -> Option<Bounds<F>>; | |
246 | ||
247 | /// Returns a scaling factor for the tolerance sequence. | |
248 | /// | |
249 | /// Typically this is the regularisation parameter. | |
250 | fn tolerance_scaling(&self) -> F; | |
251 | } | |
252 | ||
253 | /// Abstraction of regularisation terms for [`pointsource_sliding_fb_reg`]. | |
254 | pub trait SlidingRegTerm<F : Float + ToNalgebraRealField, const N : usize> | |
255 | : RegTerm<F, N> { | |
256 | /// Calculate $τ[w(z) - w(y)]$ for some w in the subdifferential of the regularisation | |
257 | /// term, such that $-ε ≤ τw - d ≤ ε$. | |
258 | fn goodness<G, BT>( | |
259 | &self, | |
260 | d : &mut BTFN<F, G, BT, N>, | |
261 | μ : &DiscreteMeasure<Loc<F, N>, F>, | |
262 | y : &Loc<F, N>, | |
263 | z : &Loc<F, N>, | |
264 | τ : F, | |
265 | ε : F, | |
266 | config : &FBGenericConfig<F>, | |
267 | ) -> F | |
268 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
269 | G : SupportGenerator<F, N, Id=BT::Data>, | |
270 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
271 | + LocalAnalysis<F, Bounds<F>, N>; | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
272 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
273 | /// Convert bound on the regulariser to a bond on the Radon norm |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
274 | fn radon_norm_bound(&self, b : F) -> F; |
32 | 275 | } |
276 | ||
277 | #[replace_float_literals(F::cast_from(literal))] | |
278 | impl<F : Float + ToNalgebraRealField, const N : usize> RegTerm<F, N> | |
279 | for NonnegRadonRegTerm<F> | |
280 | where Cube<F, N> : P2Minimise<Loc<F, N>, F> { | |
281 | fn solve_findim( | |
282 | &self, | |
283 | mA : &DMatrix<F::MixedType>, | |
284 | g : &DVector<F::MixedType>, | |
285 | τ : F, | |
286 | x : &mut DVector<F::MixedType>, | |
287 | mA_normest : F, | |
288 | ε : F, | |
289 | config : &FBGenericConfig<F> | |
290 | ) -> usize { | |
291 | let inner_tolerance = ε * config.inner.tolerance_mult; | |
292 | let inner_it = config.inner.iterator_options.stop_target(inner_tolerance); | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
293 | quadratic_nonneg(mA, g, τ * self.α(), x, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
294 | mA_normest, &config.inner, inner_it) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
295 | |
32 | 296 | } |
297 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
298 | fn solve_findim_l1squared( |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
299 | &self, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
300 | y : &DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
301 | g : &DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
302 | τ : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
303 | x : &mut DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
304 | ε : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
305 | config : &FBGenericConfig<F> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
306 | ) -> usize { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
307 | let inner_tolerance = ε * config.inner.tolerance_mult; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
308 | let inner_it = config.inner.iterator_options.stop_target(inner_tolerance); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
309 | l1squared_nonneg(y, g, τ * self.α(), 1.0, x, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
310 | &config.inner, inner_it) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
311 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
312 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
313 | |
32 | 314 | #[inline] |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
315 | fn find_tolerance_violation_slack<G, BT>( |
32 | 316 | &self, |
317 | d : &mut BTFN<F, G, BT, N>, | |
318 | τ : F, | |
319 | ε : F, | |
320 | skip_by_rough_check : bool, | |
321 | config : &FBGenericConfig<F>, | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
322 | slack : F |
32 | 323 | ) -> Option<(Loc<F, N>, F, bool)> |
324 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
325 | G : SupportGenerator<F, N, Id=BT::Data>, | |
326 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
327 | + LocalAnalysis<F, Bounds<F>, N> { | |
328 | let τα = τ * self.α(); | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
329 | let keep_below = τα + slack + ε; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
330 | let maximise_above = τα + slack + ε * config.insertion_cutoff_factor; |
32 | 331 | let refinement_tolerance = ε * config.refinement.tolerance_mult; |
332 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
333 | // If preliminary check indicates that we are in bounds, and if it otherwise matches |
32 | 334 | // the insertion strategy, skip insertion. |
335 | if skip_by_rough_check && d.bounds().upper() <= keep_below { | |
336 | None | |
337 | } else { | |
338 | // If the rough check didn't indicate no insertion needed, find maximising point. | |
339 | d.maximise_above(maximise_above, refinement_tolerance, config.refinement.max_steps) | |
340 | .map(|(ξ, v_ξ)| (ξ, v_ξ, v_ξ <= keep_below)) | |
341 | } | |
342 | } | |
343 | ||
344 | fn verify_merge_candidate<G, BT>( | |
345 | &self, | |
346 | d : &mut BTFN<F, G, BT, N>, | |
347 | μ : &DiscreteMeasure<Loc<F, N>, F>, | |
348 | τ : F, | |
349 | ε : F, | |
350 | config : &FBGenericConfig<F>, | |
351 | ) -> bool | |
352 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
353 | G : SupportGenerator<F, N, Id=BT::Data>, | |
354 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
355 | + LocalAnalysis<F, Bounds<F>, N> { | |
356 | let τα = τ * self.α(); | |
357 | let refinement_tolerance = ε * config.refinement.tolerance_mult; | |
358 | let merge_tolerance = config.merge_tolerance_mult * ε; | |
359 | let keep_below = τα + merge_tolerance; | |
360 | let keep_supp_above = τα - merge_tolerance; | |
361 | let bnd = d.bounds(); | |
362 | ||
363 | return ( | |
364 | bnd.lower() >= keep_supp_above | |
365 | || | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
366 | μ.iter_spikes().all(|&DeltaMeasure{ α, ref x }| { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
367 | (α == 0.0) || d.apply(x) >= keep_supp_above |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
368 | }) |
32 | 369 | ) && ( |
370 | bnd.upper() <= keep_below | |
371 | || | |
372 | d.has_upper_bound(keep_below, refinement_tolerance, config.refinement.max_steps) | |
373 | ) | |
374 | } | |
375 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
376 | fn verify_merge_candidate_radonsq<G, BT>( |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
377 | &self, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
378 | d : &mut BTFN<F, G, BT, N>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
379 | μ : &DiscreteMeasure<Loc<F, N>, F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
380 | τ : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
381 | ε : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
382 | config : &FBGenericConfig<F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
383 | radon_μ :&DiscreteMeasure<Loc<F, N>, F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
384 | ) -> bool |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
385 | where BT : BTSearch<F, N, Agg=Bounds<F>>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
386 | G : SupportGenerator<F, N, Id=BT::Data>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
387 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
388 | + LocalAnalysis<F, Bounds<F>, N> { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
389 | let τα = τ * self.α(); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
390 | let refinement_tolerance = ε * config.refinement.tolerance_mult; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
391 | let merge_tolerance = config.merge_tolerance_mult * ε; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
392 | let slack = radon_μ.norm(Radon); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
393 | let bnd = d.bounds(); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
394 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
395 | return { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
396 | μ.both_matching(radon_μ) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
397 | .all(|(α, rα, x)| { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
398 | let v = d.apply(x); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
399 | let (l1, u1) = match α.partial_cmp(&0.0).unwrap_or(Equal) { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
400 | Greater => (τα, τα), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
401 | _ => (F::NEG_INFINITY, τα), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
402 | // Less should not happen; treated as Equal |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
403 | }; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
404 | let (l2, u2) = match rα.partial_cmp(&0.0).unwrap_or(Equal) { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
405 | Greater => (slack, slack), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
406 | Equal => (-slack, slack), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
407 | Less => (-slack, -slack), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
408 | }; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
409 | // TODO: both fail. |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
410 | (l1 + l2 - merge_tolerance <= v) && (v <= u1 + u2 + merge_tolerance) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
411 | }) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
412 | } && { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
413 | let keep_below = τα + slack + merge_tolerance; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
414 | bnd.upper() <= keep_below |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
415 | || |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
416 | d.has_upper_bound(keep_below, refinement_tolerance, config.refinement.max_steps) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
417 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
418 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
419 | |
32 | 420 | fn target_bounds(&self, τ : F, ε : F) -> Option<Bounds<F>> { |
421 | let τα = τ * self.α(); | |
422 | Some(Bounds(τα - ε, τα + ε)) | |
423 | } | |
424 | ||
425 | fn tolerance_scaling(&self) -> F { | |
426 | self.α() | |
427 | } | |
428 | } | |
429 | ||
430 | #[replace_float_literals(F::cast_from(literal))] | |
431 | impl<F : Float + ToNalgebraRealField, const N : usize> SlidingRegTerm<F, N> | |
432 | for NonnegRadonRegTerm<F> | |
433 | where Cube<F, N> : P2Minimise<Loc<F, N>, F> { | |
434 | ||
435 | fn goodness<G, BT>( | |
436 | &self, | |
437 | d : &mut BTFN<F, G, BT, N>, | |
438 | _μ : &DiscreteMeasure<Loc<F, N>, F>, | |
439 | y : &Loc<F, N>, | |
440 | z : &Loc<F, N>, | |
441 | τ : F, | |
442 | ε : F, | |
443 | _config : &FBGenericConfig<F>, | |
444 | ) -> F | |
445 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
446 | G : SupportGenerator<F, N, Id=BT::Data>, | |
447 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
448 | + LocalAnalysis<F, Bounds<F>, N> { | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
449 | let w = |x| 1.0.min((ε + d.apply(x))/(τ * self.α())); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
450 | w(z) - w(y) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
451 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
452 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
453 | fn radon_norm_bound(&self, b : F) -> F { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
454 | b / self.α() |
32 | 455 | } |
456 | } | |
457 | ||
458 | #[replace_float_literals(F::cast_from(literal))] | |
459 | impl<F : Float + ToNalgebraRealField, const N : usize> RegTerm<F, N> for RadonRegTerm<F> | |
460 | where Cube<F, N> : P2Minimise<Loc<F, N>, F> { | |
461 | fn solve_findim( | |
462 | &self, | |
463 | mA : &DMatrix<F::MixedType>, | |
464 | g : &DVector<F::MixedType>, | |
465 | τ : F, | |
466 | x : &mut DVector<F::MixedType>, | |
467 | mA_normest: F, | |
468 | ε : F, | |
469 | config : &FBGenericConfig<F> | |
470 | ) -> usize { | |
471 | let inner_tolerance = ε * config.inner.tolerance_mult; | |
472 | let inner_it = config.inner.iterator_options.stop_target(inner_tolerance); | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
473 | quadratic_unconstrained(mA, g, τ * self.α(), x, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
474 | mA_normest, &config.inner, inner_it) |
32 | 475 | } |
476 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
477 | fn solve_findim_l1squared( |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
478 | &self, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
479 | y : &DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
480 | g : &DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
481 | τ : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
482 | x : &mut DVector<F::MixedType>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
483 | ε : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
484 | config : &FBGenericConfig<F> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
485 | ) -> usize { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
486 | let inner_tolerance = ε * config.inner.tolerance_mult; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
487 | let inner_it = config.inner.iterator_options.stop_target(inner_tolerance); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
488 | l1squared_unconstrained(y, g, τ * self.α(), 1.0, x, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
489 | &config.inner, inner_it) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
490 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
491 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
492 | fn find_tolerance_violation_slack<G, BT>( |
32 | 493 | &self, |
494 | d : &mut BTFN<F, G, BT, N>, | |
495 | τ : F, | |
496 | ε : F, | |
497 | skip_by_rough_check : bool, | |
498 | config : &FBGenericConfig<F>, | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
499 | slack : F, |
32 | 500 | ) -> Option<(Loc<F, N>, F, bool)> |
501 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
502 | G : SupportGenerator<F, N, Id=BT::Data>, | |
503 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
504 | + LocalAnalysis<F, Bounds<F>, N> { | |
505 | let τα = τ * self.α(); | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
506 | let keep_below = τα + slack + ε; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
507 | let keep_above = -(τα + slack) - ε; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
508 | let maximise_above = τα + slack + ε * config.insertion_cutoff_factor; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
509 | let minimise_below = -(τα + slack) - ε * config.insertion_cutoff_factor; |
32 | 510 | let refinement_tolerance = ε * config.refinement.tolerance_mult; |
511 | ||
512 | // If preliminary check indicates that we are in bonds, and if it otherwise matches | |
513 | // the insertion strategy, skip insertion. | |
514 | if skip_by_rough_check && Bounds(keep_above, keep_below).superset(&d.bounds()) { | |
515 | None | |
516 | } else { | |
517 | // If the rough check didn't indicate no insertion needed, find maximising point. | |
518 | let mx = d.maximise_above(maximise_above, refinement_tolerance, | |
519 | config.refinement.max_steps); | |
520 | let mi = d.minimise_below(minimise_below, refinement_tolerance, | |
521 | config.refinement.max_steps); | |
522 | ||
523 | match (mx, mi) { | |
524 | (None, None) => None, | |
525 | (Some((ξ, v_ξ)), None) => Some((ξ, v_ξ, keep_below >= v_ξ)), | |
526 | (None, Some((ζ, v_ζ))) => Some((ζ, v_ζ, keep_above <= v_ζ)), | |
527 | (Some((ξ, v_ξ)), Some((ζ, v_ζ))) => { | |
528 | if v_ξ - τα > τα - v_ζ { | |
529 | Some((ξ, v_ξ, keep_below >= v_ξ)) | |
530 | } else { | |
531 | Some((ζ, v_ζ, keep_above <= v_ζ)) | |
532 | } | |
533 | } | |
534 | } | |
535 | } | |
536 | } | |
537 | ||
538 | fn verify_merge_candidate<G, BT>( | |
539 | &self, | |
540 | d : &mut BTFN<F, G, BT, N>, | |
541 | μ : &DiscreteMeasure<Loc<F, N>, F>, | |
542 | τ : F, | |
543 | ε : F, | |
544 | config : &FBGenericConfig<F>, | |
545 | ) -> bool | |
546 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
547 | G : SupportGenerator<F, N, Id=BT::Data>, | |
548 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
549 | + LocalAnalysis<F, Bounds<F>, N> { | |
550 | let τα = τ * self.α(); | |
551 | let refinement_tolerance = ε * config.refinement.tolerance_mult; | |
552 | let merge_tolerance = config.merge_tolerance_mult * ε; | |
553 | let keep_below = τα + merge_tolerance; | |
554 | let keep_above = -τα - merge_tolerance; | |
555 | let keep_supp_pos_above = τα - merge_tolerance; | |
556 | let keep_supp_neg_below = -τα + merge_tolerance; | |
557 | let bnd = d.bounds(); | |
558 | ||
559 | return ( | |
560 | (bnd.lower() >= keep_supp_pos_above && bnd.upper() <= keep_supp_neg_below) | |
561 | || | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
562 | μ.iter_spikes().all(|&DeltaMeasure{ α : β, ref x }| { |
32 | 563 | match β.partial_cmp(&0.0) { |
564 | Some(Greater) => d.apply(x) >= keep_supp_pos_above, | |
565 | Some(Less) => d.apply(x) <= keep_supp_neg_below, | |
566 | _ => true, | |
567 | } | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
568 | }) |
32 | 569 | ) && ( |
570 | bnd.upper() <= keep_below | |
571 | || | |
572 | d.has_upper_bound(keep_below, refinement_tolerance, | |
573 | config.refinement.max_steps) | |
574 | ) && ( | |
575 | bnd.lower() >= keep_above | |
576 | || | |
577 | d.has_lower_bound(keep_above, refinement_tolerance, | |
578 | config.refinement.max_steps) | |
579 | ) | |
580 | } | |
581 | ||
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
582 | fn verify_merge_candidate_radonsq<G, BT>( |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
583 | &self, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
584 | d : &mut BTFN<F, G, BT, N>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
585 | μ : &DiscreteMeasure<Loc<F, N>, F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
586 | τ : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
587 | ε : F, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
588 | config : &FBGenericConfig<F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
589 | radon_μ : &DiscreteMeasure<Loc<F, N>, F>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
590 | ) -> bool |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
591 | where BT : BTSearch<F, N, Agg=Bounds<F>>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
592 | G : SupportGenerator<F, N, Id=BT::Data>, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
593 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
594 | + LocalAnalysis<F, Bounds<F>, N> { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
595 | let τα = τ * self.α(); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
596 | let refinement_tolerance = ε * config.refinement.tolerance_mult; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
597 | let merge_tolerance = config.merge_tolerance_mult * ε; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
598 | let slack = radon_μ.norm(Radon); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
599 | let bnd = d.bounds(); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
600 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
601 | return { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
602 | μ.both_matching(radon_μ) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
603 | .all(|(α, rα, x)| { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
604 | let v = d.apply(x); |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
605 | let (l1, u1) = match α.partial_cmp(&0.0).unwrap_or(Equal) { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
606 | Greater => (τα, τα), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
607 | Equal => (-τα, τα), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
608 | Less => (-τα, -τα), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
609 | }; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
610 | let (l2, u2) = match rα.partial_cmp(&0.0).unwrap_or(Equal) { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
611 | Greater => (slack, slack), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
612 | Equal => (-slack, slack), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
613 | Less => (-slack, -slack), |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
614 | }; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
615 | (l1 + l2 - merge_tolerance <= v) && (v <= u1 + u2 + merge_tolerance) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
616 | }) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
617 | } && { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
618 | let keep_below = τα + slack + merge_tolerance; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
619 | bnd.upper() <= keep_below |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
620 | || |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
621 | d.has_upper_bound(keep_below, refinement_tolerance, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
622 | config.refinement.max_steps) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
623 | } && { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
624 | let keep_above = -τα - slack - merge_tolerance; |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
625 | bnd.lower() >= keep_above |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
626 | || |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
627 | d.has_lower_bound(keep_above, refinement_tolerance, |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
628 | config.refinement.max_steps) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
629 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
630 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
631 | |
32 | 632 | fn target_bounds(&self, τ : F, ε : F) -> Option<Bounds<F>> { |
633 | let τα = τ * self.α(); | |
634 | Some(Bounds(-τα - ε, τα + ε)) | |
635 | } | |
636 | ||
637 | fn tolerance_scaling(&self) -> F { | |
638 | self.α() | |
639 | } | |
640 | } | |
641 | ||
642 | #[replace_float_literals(F::cast_from(literal))] | |
643 | impl<F : Float + ToNalgebraRealField, const N : usize> SlidingRegTerm<F, N> | |
644 | for RadonRegTerm<F> | |
645 | where Cube<F, N> : P2Minimise<Loc<F, N>, F> { | |
646 | ||
647 | fn goodness<G, BT>( | |
648 | &self, | |
649 | d : &mut BTFN<F, G, BT, N>, | |
650 | _μ : &DiscreteMeasure<Loc<F, N>, F>, | |
651 | y : &Loc<F, N>, | |
652 | z : &Loc<F, N>, | |
653 | τ : F, | |
654 | ε : F, | |
655 | _config : &FBGenericConfig<F>, | |
656 | ) -> F | |
657 | where BT : BTSearch<F, N, Agg=Bounds<F>>, | |
658 | G : SupportGenerator<F, N, Id=BT::Data>, | |
659 | G::SupportType : Mapping<Loc<F, N>,Codomain=F> | |
660 | + LocalAnalysis<F, Bounds<F>, N> { | |
661 | ||
662 | let α = self.α(); | |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
663 | let w = |x| { |
32 | 664 | let dx = d.apply(x); |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
665 | ((-ε + dx)/(τ * α)).max(1.0.min(ε + dx)/(τ * α)) |
32 | 666 | }; |
34
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
667 | w(z) - w(y) |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
668 | } |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
669 | |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
670 | fn radon_norm_bound(&self, b : F) -> F { |
efa60bc4f743
Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents:
32
diff
changeset
|
671 | b / self.α() |
32 | 672 | } |
673 | } |