src/fb.rs

Thu, 23 Jan 2025 23:34:05 +0100

author
Tuomo Valkonen <tuomov@iki.fi>
date
Thu, 23 Jan 2025 23:34:05 +0100
branch
dev
changeset 39
6316d68b58af
parent 37
c5d8bd1a7728
child 51
0693cc9ba9f0
permissions
-rw-r--r--

Merging adjustments, parameter tuning, etc.

0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
1 /*!
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
2 Solver for the point source localisation problem using a forward-backward splitting method.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
3
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
4 This corresponds to the manuscript
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
5
13
bdc57366d4f5 arXiv links, README beautification
Tuomo Valkonen <tuomov@iki.fi>
parents: 8
diff changeset
6 * Valkonen T. - _Proximal methods for point source localisation_,
bdc57366d4f5 arXiv links, README beautification
Tuomo Valkonen <tuomov@iki.fi>
parents: 8
diff changeset
7 [arXiv:2212.02991](https://arxiv.org/abs/2212.02991).
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
8
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
9 The main routine is [`pointsource_fb_reg`].
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
10
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
11 ## Problem
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
12
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
13 <p>
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
14 Our objective is to solve
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
15 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
16 \min_{μ ∈ ℳ(Ω)}~ F_0(Aμ-b) + α \|μ\|_{ℳ(Ω)} + δ_{≥ 0}(μ),
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
17 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
18 where $F_0(y)=\frac{1}{2}\|y\|_2^2$ and the forward operator $A \in 𝕃(ℳ(Ω); ℝ^n)$.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
19 </p>
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
20
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
21 ## Approach
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
22
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
23 <p>
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
24 As documented in more detail in the paper, on each step we approximately solve
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
25 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
26 \min_{μ ∈ ℳ(Ω)}~ F(x) + α \|μ\|_{ℳ(Ω)} + δ_{≥ 0}(x) + \frac{1}{2}\|μ-μ^k|_𝒟^2,
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
27 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
28 where $𝒟: 𝕃(ℳ(Ω); C_c(Ω))$ is typically a convolution operator.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
29 </p>
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
30
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
31 ## Finite-dimensional subproblems.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
32
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
33 With $C$ a projection from [`DiscreteMeasure`] to the weights, and $x^k$ such that $x^k=Cμ^k$, we
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
34 form the discretised linearised inner problem
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
35 <p>
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
36 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
37 \min_{x ∈ ℝ^n}~ τ\bigl(F(Cx^k) + [C^*∇F(Cx^k)]^⊤(x-x^k) + α {\vec 1}^⊤ x\bigr)
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
38 + δ_{≥ 0}(x) + \frac{1}{2}\|x-x^k\|_{C^*𝒟C}^2,
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
39 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
40 equivalently
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
41 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
42 \begin{aligned}
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
43 \min_x~ & τF(Cx^k) - τ[C^*∇F(Cx^k)]^⊤x^k + \frac{1}{2} (x^k)^⊤ C^*𝒟C x^k
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
44 \\
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
45 &
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
46 - [C^*𝒟C x^k - τC^*∇F(Cx^k)]^⊤ x
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
47 \\
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
48 &
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
49 + \frac{1}{2} x^⊤ C^*𝒟C x
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
50 + τα {\vec 1}^⊤ x + δ_{≥ 0}(x),
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
51 \end{aligned}
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
52 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
53 In other words, we obtain the quadratic non-negativity constrained problem
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
54 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
55 \min_{x ∈ ℝ^n}~ \frac{1}{2} x^⊤ Ã x - b̃^⊤ x + c + τα {\vec 1}^⊤ x + δ_{≥ 0}(x).
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
56 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
57 where
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
58 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
59 \begin{aligned}
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
60 Ã & = C^*𝒟C,
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
61 \\
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
62 g̃ & = C^*𝒟C x^k - τ C^*∇F(Cx^k)
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
63 = C^* 𝒟 μ^k - τ C^*A^*(Aμ^k - b)
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
64 \\
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
65 c & = τ F(Cx^k) - τ[C^*∇F(Cx^k)]^⊤x^k + \frac{1}{2} (x^k)^⊤ C^*𝒟C x^k
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
66 \\
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
67 &
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
68 = \frac{τ}{2} \|Aμ^k-b\|^2 - τ[Aμ^k-b]^⊤Aμ^k + \frac{1}{2} \|μ_k\|_{𝒟}^2
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
69 \\
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
70 &
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
71 = -\frac{τ}{2} \|Aμ^k-b\|^2 + τ[Aμ^k-b]^⊤ b + \frac{1}{2} \|μ_k\|_{𝒟}^2.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
72 \end{aligned}
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
73 $$
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
74 </p>
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
75
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
76 We solve this with either SSN or FB as determined by
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
77 [`InnerSettings`] in [`FBGenericConfig::inner`].
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
78 */
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
79
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
80 use numeric_literals::replace_float_literals;
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
81 use serde::{Serialize, Deserialize};
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
82 use colored::Colorize;
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
83
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
84 use alg_tools::iterate::AlgIteratorFactory;
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
85 use alg_tools::euclidean::Euclidean;
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
86 use alg_tools::linops::{Mapping, GEMV};
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
87 use alg_tools::mapping::RealMapping;
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
88 use alg_tools::nalgebra_support::ToNalgebraRealField;
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
89 use alg_tools::instance::Instance;
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
90
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
91 use crate::types::*;
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
92 use crate::measures::{
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
93 DiscreteMeasure,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
94 RNDM,
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
95 };
39
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
96 use crate::measures::merging::SpikeMerging;
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
97 use crate::forward_model::{
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
98 ForwardModel,
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
99 AdjointProductBoundedBy,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
100 };
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
101 use crate::plot::{
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
102 SeqPlotter,
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
103 Plotting,
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
104 PlotLookup
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
105 };
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
106 use crate::regularisation::RegTerm;
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
107 use crate::dataterm::{
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
108 calculate_residual,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
109 L2Squared,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
110 DataTerm,
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
111 };
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
112 pub use crate::prox_penalty::{
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
113 FBGenericConfig,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
114 ProxPenalty
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
115 };
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
116
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
117 /// Settings for [`pointsource_fb_reg`].
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
118 #[derive(Clone, Copy, Eq, PartialEq, Serialize, Deserialize, Debug)]
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
119 #[serde(default)]
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
120 pub struct FBConfig<F : Float> {
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
121 /// Step length scaling
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
122 pub τ0 : F,
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
123 /// Generic parameters
34
efa60bc4f743 Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents: 32
diff changeset
124 pub generic : FBGenericConfig<F>,
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
125 }
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
126
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
127 #[replace_float_literals(F::cast_from(literal))]
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
128 impl<F : Float> Default for FBConfig<F> {
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
129 fn default() -> Self {
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
130 FBConfig {
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
131 τ0 : 0.99,
34
efa60bc4f743 Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents: 32
diff changeset
132 generic : Default::default(),
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
133 }
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
134 }
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
135 }
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
136
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
137 pub(crate) fn prune_with_stats<F : Float, const N : usize>(
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
138 μ : &mut RNDM<F, N>,
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
139 ) -> usize {
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
140 let n_before_prune = μ.len();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
141 μ.prune();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
142 debug_assert!(μ.len() <= n_before_prune);
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
143 n_before_prune - μ.len()
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
144 }
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
145
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
146 #[replace_float_literals(F::cast_from(literal))]
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
147 pub(crate) fn postprocess<
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
148 F : Float,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
149 V : Euclidean<F> + Clone,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
150 A : GEMV<F, RNDM<F, N>, Codomain = V>,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
151 D : DataTerm<F, V, N>,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
152 const N : usize
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
153 > (
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
154 mut μ : RNDM<F, N>,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
155 config : &FBGenericConfig<F>,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
156 dataterm : D,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
157 opA : &A,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
158 b : &V,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
159 ) -> RNDM<F, N>
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
160 where
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
161 RNDM<F, N> : SpikeMerging<F>,
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
162 for<'a> &'a RNDM<F, N> : Instance<RNDM<F, N>>,
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
163 {
39
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
164 μ.merge_spikes_fitness(config.final_merging_method(),
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
165 |μ̃| dataterm.calculate_fit_op(μ̃, opA, b),
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
166 |&v| v);
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
167 μ.prune();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
168 μ
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
169 }
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
170
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
171 /// Iteratively solve the pointsource localisation problem using forward-backward splitting.
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
172 ///
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
173 /// The settings in `config` have their [respective documentation](FBConfig). `opA` is the
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
174 /// forward operator $A$, $b$ the observable, and $\lambda$ the regularisation weight.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
175 /// The operator `op𝒟` is used for forming the proximal term. Typically it is a convolution
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
176 /// operator. Finally, the `iterator` is an outer loop verbosity and iteration count control
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
177 /// as documented in [`alg_tools::iterate`].
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
178 ///
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
179 /// For details on the mathematical formulation, see the [module level](self) documentation.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
180 ///
0
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
181 /// The implementation relies on [`alg_tools::bisection_tree::BTFN`] presentations of
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
182 /// sums of simple functions usign bisection trees, and the related
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
183 /// [`alg_tools::bisection_tree::Aggregator`]s, to efficiently search for component functions
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
184 /// active at a specific points, and to maximise their sums. Through the implementation of the
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
185 /// [`alg_tools::bisection_tree::BT`] bisection trees, it also relies on the copy-on-write features
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
186 /// of [`std::sync::Arc`] to only update relevant parts of the bisection tree when adding functions.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
187 ///
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
188 /// Returns the final iterate.
eb3c7813b67a Initial version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
189 #[replace_float_literals(F::cast_from(literal))]
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
190 pub fn pointsource_fb_reg<
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
191 F, I, A, Reg, P, const N : usize
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
192 >(
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
193 opA : &A,
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
194 b : &A::Observable,
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
195 reg : Reg,
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
196 prox_penalty : &P,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
197 fbconfig : &FBConfig<F>,
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
198 iterator : I,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
199 mut plotter : SeqPlotter<F, N>,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
200 ) -> RNDM<F, N>
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
201 where
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
202 F : Float + ToNalgebraRealField,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
203 I : AlgIteratorFactory<IterInfo<F, N>>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
204 for<'b> &'b A::Observable : std::ops::Neg<Output=A::Observable>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
205 A : ForwardModel<RNDM<F, N>, F>
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
206 + AdjointProductBoundedBy<RNDM<F, N>, P, FloatType=F>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
207 A::PreadjointCodomain : RealMapping<F, N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
208 PlotLookup : Plotting<N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
209 RNDM<F, N> : SpikeMerging<F>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
210 Reg : RegTerm<F, N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
211 P : ProxPenalty<F, A::PreadjointCodomain, Reg, N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
212 {
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
213
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
214 // Set up parameters
34
efa60bc4f743 Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents: 32
diff changeset
215 let config = &fbconfig.generic;
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
216 let τ = fbconfig.τ0/opA.adjoint_product_bound(prox_penalty).unwrap();
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
217 // We multiply tolerance by τ for FB since our subproblems depending on tolerances are scaled
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
218 // by τ compared to the conditional gradient approach.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
219 let tolerance = config.tolerance * τ * reg.tolerance_scaling();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
220 let mut ε = tolerance.initial();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
221
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
222 // Initialise iterates
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
223 let mut μ = DiscreteMeasure::new();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
224 let mut residual = -b;
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
225
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
226 // Statistics
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
227 let full_stats = |residual : &A::Observable,
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
228 μ : &RNDM<F, N>,
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
229 ε, stats| IterInfo {
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
230 value : residual.norm2_squared_div2() + reg.apply(μ),
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
231 n_spikes : μ.len(),
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
232 ε,
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
233 //postprocessing: config.postprocessing.then(|| μ.clone()),
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
234 .. stats
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
235 };
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
236 let mut stats = IterInfo::new();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
237
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
238 // Run the algorithm
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
239 for state in iterator.iter_init(|| full_stats(&residual, &μ, ε, stats.clone())) {
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
240 // Calculate smooth part of surrogate model.
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
241 let mut τv = opA.preadjoint().apply(residual * τ);
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
242
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
243 // Save current base point
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
244 let μ_base = μ.clone();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
245
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
246 // Insert and reweigh
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
247 let (maybe_d, _within_tolerances) = prox_penalty.insert_and_reweigh(
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
248 &mut μ, &mut τv, &μ_base, None,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
249 τ, ε,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
250 config, &reg, &state, &mut stats
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
251 );
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
252
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
253 // Prune and possibly merge spikes
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
254 if config.merge_now(&state) {
39
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
255 stats.merged += prox_penalty.merge_spikes(
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
256 &mut μ, &mut τv, &μ_base, None, τ, ε, config, &reg,
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
257 Some(|μ̃ : &RNDM<F, N>| L2Squared.calculate_fit_op(μ̃, opA, b)),
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
258 );
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
259 }
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
260
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
261 stats.pruned += prune_with_stats(&mut μ);
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
262
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
263 // Update residual
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
264 residual = calculate_residual(&μ, opA, b);
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
265
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
266 let iter = state.iteration();
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
267 stats.this_iters += 1;
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
268
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
269 // Give statistics if needed
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
270 state.if_verbose(|| {
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
271 plotter.plot_spikes(iter, maybe_d.as_ref(), Some(&τv), &μ);
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
272 full_stats(&residual, &μ, ε, std::mem::replace(&mut stats, IterInfo::new()))
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
273 });
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
274
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
275 // Update main tolerance for next iteration
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
276 ε = tolerance.update(ε, iter);
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
277 }
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
278
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
279 postprocess(μ, config, L2Squared, opA, b)
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
280 }
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
281
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
282 /// Iteratively solve the pointsource localisation problem using inertial forward-backward splitting.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
283 ///
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
284 /// The settings in `config` have their [respective documentation](FBConfig). `opA` is the
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
285 /// forward operator $A$, $b$ the observable, and $\lambda$ the regularisation weight.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
286 /// The operator `op𝒟` is used for forming the proximal term. Typically it is a convolution
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
287 /// operator. Finally, the `iterator` is an outer loop verbosity and iteration count control
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
288 /// as documented in [`alg_tools::iterate`].
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
289 ///
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
290 /// For details on the mathematical formulation, see the [module level](self) documentation.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
291 ///
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
292 /// The implementation relies on [`alg_tools::bisection_tree::BTFN`] presentations of
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
293 /// sums of simple functions usign bisection trees, and the related
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
294 /// [`alg_tools::bisection_tree::Aggregator`]s, to efficiently search for component functions
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
295 /// active at a specific points, and to maximise their sums. Through the implementation of the
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
296 /// [`alg_tools::bisection_tree::BT`] bisection trees, it also relies on the copy-on-write features
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
297 /// of [`std::sync::Arc`] to only update relevant parts of the bisection tree when adding functions.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
298 ///
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
299 /// Returns the final iterate.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
300 #[replace_float_literals(F::cast_from(literal))]
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
301 pub fn pointsource_fista_reg<
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
302 F, I, A, Reg, P, const N : usize
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
303 >(
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
304 opA : &A,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
305 b : &A::Observable,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
306 reg : Reg,
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
307 prox_penalty : &P,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
308 fbconfig : &FBConfig<F>,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
309 iterator : I,
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
310 mut plotter : SeqPlotter<F, N>,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
311 ) -> RNDM<F, N>
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
312 where
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
313 F : Float + ToNalgebraRealField,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
314 I : AlgIteratorFactory<IterInfo<F, N>>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
315 for<'b> &'b A::Observable : std::ops::Neg<Output=A::Observable>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
316 A : ForwardModel<RNDM<F, N>, F>
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
317 + AdjointProductBoundedBy<RNDM<F, N>, P, FloatType=F>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
318 A::PreadjointCodomain : RealMapping<F, N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
319 PlotLookup : Plotting<N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
320 RNDM<F, N> : SpikeMerging<F>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
321 Reg : RegTerm<F, N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
322 P : ProxPenalty<F, A::PreadjointCodomain, Reg, N>,
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
323 {
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
324
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
325 // Set up parameters
34
efa60bc4f743 Radon FB + sliding improvements
Tuomo Valkonen <tuomov@iki.fi>
parents: 32
diff changeset
326 let config = &fbconfig.generic;
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
327 let τ = fbconfig.τ0/opA.adjoint_product_bound(prox_penalty).unwrap();
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
328 let mut λ = 1.0;
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
329 // We multiply tolerance by τ for FB since our subproblems depending on tolerances are scaled
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
330 // by τ compared to the conditional gradient approach.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
331 let tolerance = config.tolerance * τ * reg.tolerance_scaling();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
332 let mut ε = tolerance.initial();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
333
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
334 // Initialise iterates
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
335 let mut μ = DiscreteMeasure::new();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
336 let mut μ_prev = DiscreteMeasure::new();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
337 let mut residual = -b;
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
338 let mut warned_merging = false;
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
339
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
340 // Statistics
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
341 let full_stats = |ν : &RNDM<F, N>, ε, stats| IterInfo {
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
342 value : L2Squared.calculate_fit_op(ν, opA, b) + reg.apply(ν),
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
343 n_spikes : ν.len(),
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
344 ε,
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
345 // postprocessing: config.postprocessing.then(|| ν.clone()),
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
346 .. stats
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
347 };
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
348 let mut stats = IterInfo::new();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
349
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
350 // Run the algorithm
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
351 for state in iterator.iter_init(|| full_stats(&μ, ε, stats.clone())) {
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
352 // Calculate smooth part of surrogate model.
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
353 let mut τv = opA.preadjoint().apply(residual * τ);
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
354
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
355 // Save current base point
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
356 let μ_base = μ.clone();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
357
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
358 // Insert new spikes and reweigh
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
359 let (maybe_d, _within_tolerances) = prox_penalty.insert_and_reweigh(
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
360 &mut μ, &mut τv, &μ_base, None,
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
361 τ, ε,
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
362 config, &reg, &state, &mut stats
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
363 );
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
364
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
365 // (Do not) merge spikes.
39
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
366 if config.merge_now(&state) && !warned_merging {
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
367 let err = format!("Merging not supported for μFISTA");
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
368 println!("{}", err.red());
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
369 warned_merging = true;
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
370 }
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
371
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
372 // Update inertial prameters
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
373 let λ_prev = λ;
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
374 λ = 2.0 * λ_prev / ( λ_prev + (4.0 + λ_prev * λ_prev).sqrt() );
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
375 let θ = λ / λ_prev - λ;
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
376
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
377 // Perform inertial update on μ.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
378 // This computes μ ← (1 + θ) * μ - θ * μ_prev, pruning spikes where both μ
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
379 // and μ_prev have zero weight. Since both have weights from the finite-dimensional
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
380 // subproblem with a proximal projection step, this is likely to happen when the
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
381 // spike is not needed. A copy of the pruned μ without artithmetic performed is
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
382 // stored in μ_prev.
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
383 let n_before_prune = μ.len();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
384 μ.pruning_sub(1.0 + θ, θ, &mut μ_prev);
39
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
385 //let μ_new = (&μ * (1.0 + θ)).sub_matching(&(&μ_prev * θ));
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
386 // μ_prev = μ;
6316d68b58af Merging adjustments, parameter tuning, etc.
Tuomo Valkonen <tuomov@iki.fi>
parents: 37
diff changeset
387 // μ = μ_new;
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
388 debug_assert!(μ.len() <= n_before_prune);
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
389 stats.pruned += n_before_prune - μ.len();
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
390
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
391 // Update residual
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
392 residual = calculate_residual(&μ, opA, b);
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
393
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
394 let iter = state.iteration();
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
395 stats.this_iters += 1;
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
396
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
397 // Give statistics if needed
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
398 state.if_verbose(|| {
37
c5d8bd1a7728 Generic proximal penalty support
Tuomo Valkonen <tuomov@iki.fi>
parents: 35
diff changeset
399 plotter.plot_spikes(iter, maybe_d.as_ref(), Some(&τv), &μ_prev);
35
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
400 full_stats(&μ_prev, ε, std::mem::replace(&mut stats, IterInfo::new()))
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
401 });
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
402
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
403 // Update main tolerance for next iteration
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
404 ε = tolerance.update(ε, iter);
b087e3eab191 New version of sliding.
Tuomo Valkonen <tuomov@iki.fi>
parents: 34
diff changeset
405 }
32
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
406
56c8adc32b09 Early transport sketches
Tuomo Valkonen <tuomov@iki.fi>
parents: 29
diff changeset
407 postprocess(μ_prev, config, L2Squared, opA, b)
24
d29d1fcf5423 Support arbitrary regularisation terms; implement non-positivity-constrained regularisation.
Tuomo Valkonen <tuomov@iki.fi>
parents: 13
diff changeset
408 }

mercurial