| 19 use crate::pdps::PDPSConfig; |
19 use crate::pdps::PDPSConfig; |
| 20 use crate::types::*; |
20 use crate::types::*; |
| 21 use crate::run::{ |
21 use crate::run::{ |
| 22 RunnableExperiment, |
22 RunnableExperiment, |
| 23 ExperimentV2, |
23 ExperimentV2, |
| |
24 ExperimentBiased, |
| 24 Named, |
25 Named, |
| 25 DefaultAlgorithm, |
26 DefaultAlgorithm, |
| 26 AlgorithmConfig |
27 AlgorithmConfig |
| 27 }; |
28 }; |
| 28 //use crate::fb::FBGenericConfig; |
29 //use crate::fb::FBGenericConfig; |
| 29 use crate::rand_distr::{SerializableNormal, SaltAndPepper}; |
30 use crate::rand_distr::{SerializableNormal, SaltAndPepper}; |
| 30 use crate::regularisation::Regularisation; |
31 use crate::regularisation::Regularisation; |
| |
32 use alg_tools::euclidean::Euclidean; |
| |
33 use alg_tools::instance::Instance; |
| |
34 use alg_tools::mapping::Mapping; |
| |
35 use alg_tools::operator_arithmetic::{MappingSum, Weighted}; |
| 31 |
36 |
| 32 /// Experiments shorthands, to be used with the command line parser |
37 /// Experiments shorthands, to be used with the command line parser |
| 33 |
38 |
| 34 #[derive(ValueEnum, Debug, Copy, Clone, Eq, PartialEq, Hash, Serialize, Deserialize)] |
39 #[derive(ValueEnum, Debug, Copy, Clone, Eq, PartialEq, Hash, Serialize, Deserialize)] |
| 35 #[allow(non_camel_case_types)] |
40 #[allow(non_camel_case_types)] |
| 56 #[clap(name = "2d_l1")] |
61 #[clap(name = "2d_l1")] |
| 57 Experiment2D_L1, |
62 Experiment2D_L1, |
| 58 /// Two dimensions, “fast” spread, 1-norm data fidelity |
63 /// Two dimensions, “fast” spread, 1-norm data fidelity |
| 59 #[clap(name = "2d_l1_fast")] |
64 #[clap(name = "2d_l1_fast")] |
| 60 Experiment2D_L1_Fast, |
65 Experiment2D_L1_Fast, |
| |
66 /// One dimension, “fast” spread, 2-norm-squared data fidelity with extra TV-regularised bias |
| |
67 #[clap(name = "1d_tv_fast")] |
| |
68 Experiment1D_TV_Fast, |
| 61 } |
69 } |
| 62 |
70 |
| 63 macro_rules! make_float_constant { |
71 macro_rules! make_float_constant { |
| 64 ($name:ident = $value:expr) => { |
72 ($name:ident = $value:expr) => { |
| 65 #[derive(Debug, Copy, Eq, PartialEq, Clone, Serialize, Deserialize)] |
73 #[derive(Debug, Copy, Eq, PartialEq, Clone, Serialize, Deserialize)] |
| 90 ([0.75, 0.45], 2.0), |
98 ([0.75, 0.45], 2.0), |
| 91 ([0.80, 0.50], 4.0), |
99 ([0.80, 0.50], 4.0), |
| 92 ([0.30, 0.70], 5.0) |
100 ([0.30, 0.70], 5.0) |
| 93 ]; |
101 ]; |
| 94 |
102 |
| |
103 /// The $\{0,1\}$-valued characteristic function of a ball as a [`Mapping`]. |
| |
104 #[derive(Debug,Copy,Clone,Serialize,PartialEq)] |
| |
105 struct BallCharacteristic<F : Float, const N : usize> { |
| |
106 pub center : Loc<F, N>, |
| |
107 pub radius : F, |
| |
108 } |
| |
109 |
| |
110 impl<F : Float, const N : usize> Mapping<Loc<F, N>> for BallCharacteristic<F, N> { |
| |
111 type Codomain =F; |
| |
112 |
| |
113 fn apply<I : Instance<Loc<F, N>>>(&self, i : I) -> F { |
| |
114 if self.center.dist2(i) <= self.radius { |
| |
115 F::ONE |
| |
116 } else { |
| |
117 F::ZERO |
| |
118 } |
| |
119 } |
| |
120 } |
| |
121 |
| 95 //#[replace_float_literals(F::cast_from(literal))] |
122 //#[replace_float_literals(F::cast_from(literal))] |
| 96 impl DefaultExperiment { |
123 impl DefaultExperiment { |
| 97 /// Convert the experiment shorthand into a runnable experiment configuration. |
124 /// Convert the experiment shorthand into a runnable experiment configuration. |
| 98 pub fn get_experiment(&self, cli : &ExperimentOverrides<float>) -> DynResult<Box<dyn RunnableExperiment<float>>> { |
125 pub fn get_experiment(&self, cli : &ExperimentOverrides<float>) -> DynResult<Box<dyn RunnableExperiment<float>>> { |
| 99 let name = "pointsource".to_string() |
126 let name = "pointsource".to_string() |
| 113 make_float_constant!(SensorWidth2DMore = 0.4/(N_SENSORS_2D_MORE as float)); |
140 make_float_constant!(SensorWidth2DMore = 0.4/(N_SENSORS_2D_MORE as float)); |
| 114 |
141 |
| 115 make_float_constant!(Variance1 = 0.05.powi(2)); |
142 make_float_constant!(Variance1 = 0.05.powi(2)); |
| 116 make_float_constant!(CutOff1 = 0.15); |
143 make_float_constant!(CutOff1 = 0.15); |
| 117 make_float_constant!(Hat1 = 0.16); |
144 make_float_constant!(Hat1 = 0.16); |
| |
145 make_float_constant!(HatBias = 0.05); |
| 118 |
146 |
| 119 // We use a different step length for PDPS in 2D experiments |
147 // We use a different step length for PDPS in 2D experiments |
| 120 let pdps_2d = || { |
148 let pdps_2d = || { |
| 121 let τ0 = 3.0; |
149 let τ0 = 3.0; |
| 122 PDPSConfig { |
150 PDPSConfig { |
| 292 algorithm_defaults: HashMap::from([ |
320 algorithm_defaults: HashMap::from([ |
| 293 (DefaultAlgorithm::PDPS, AlgorithmConfig::PDPS(pdps_2d())) |
321 (DefaultAlgorithm::PDPS, AlgorithmConfig::PDPS(pdps_2d())) |
| 294 ]), |
322 ]), |
| 295 }}) |
323 }}) |
| 296 }, |
324 }, |
| |
325 Experiment1D_TV_Fast => { |
| |
326 let base_spread = HatConv { radius : HatBias }; |
| |
327 Box::new(Named { name, data : ExperimentBiased { |
| |
328 λ : 0.02, |
| |
329 bias : MappingSum::new([ |
| |
330 Weighted::new(1.0, BallCharacteristic{ center : 0.3.into(), radius : 0.2 }), |
| |
331 Weighted::new(0.5, BallCharacteristic{ center : 0.6.into(), radius : 0.3 }), |
| |
332 ]), |
| |
333 base : ExperimentV2 { |
| |
334 domain : [[0.0, 1.0]].into(), |
| |
335 sensor_count : [N_SENSORS_1D], |
| |
336 regularisation : Regularisation::NonnegRadon(cli.alpha.unwrap_or(0.2)), |
| |
337 noise_distr : SerializableNormal::new(0.0, cli.variance.unwrap_or(0.1))?, |
| |
338 dataterm : DataTerm::L2Squared, |
| |
339 μ_hat : MU_TRUE_1D_BASIC.into(), |
| |
340 sensor : BallIndicator { r : SensorWidth1D, exponent : Linfinity }, |
| |
341 spread : base_spread, |
| |
342 kernel : base_spread, |
| |
343 kernel_plot_width, |
| |
344 noise_seed, |
| |
345 algorithm_defaults: HashMap::new(), |
| |
346 }, |
| |
347 }}) |
| |
348 }, |
| 297 }) |
349 }) |
| 298 } |
350 } |
| 299 } |
351 } |
| 300 |
352 |