spin_sim/statistics/
results.rs1use super::equilibration::EquilCheckpoint;
2
3pub const OVERLAP_HIST_BINS: usize = 200;
4
5pub struct ClusterStats {
6 pub fk_csd: Vec<Vec<u64>>,
8 pub overlap_csd: Vec<Vec<u64>>,
10 pub top_cluster_sizes: Vec<[f64; 4]>,
13}
14
15pub struct Diagnostics {
16 pub mags2_tau: Vec<f64>,
19 pub overlap2_tau: Vec<f64>,
22 pub equil_checkpoints: Vec<EquilCheckpoint>,
25}
26
27pub struct SweepResult {
32 pub mags: Vec<f64>,
34 pub mags2: Vec<f64>,
36 pub mags4: Vec<f64>,
38 pub energies: Vec<f64>,
40 pub energies2: Vec<f64>,
42 pub overlap: Vec<f64>,
44 pub overlap2: Vec<f64>,
46 pub overlap4: Vec<f64>,
48 pub overlap_histogram: Vec<Vec<u64>>,
51 pub cluster_stats: ClusterStats,
52 pub diagnostics: Diagnostics,
53}
54
55impl SweepResult {
56 pub fn aggregate(results: &[Self]) -> Self {
58 let n = results.len() as f64;
59 let n_temps = results[0].mags.len();
60 let n_overlap = results[0].overlap.len();
61 let n_overlap_hist = results[0].overlap_histogram.len();
62 let n_fk_csd = results[0].cluster_stats.fk_csd.len();
63 let n_ov_csd = results[0].cluster_stats.overlap_csd.len();
64
65 let fk_len = results[0]
66 .cluster_stats
67 .fk_csd
68 .first()
69 .map_or(0, |v| v.len());
70 let ov_len = results[0]
71 .cluster_stats
72 .overlap_csd
73 .first()
74 .map_or(0, |v| v.len());
75
76 let n_top = results[0].cluster_stats.top_cluster_sizes.len();
77
78 let m2_tau_len = results[0].diagnostics.mags2_tau.len();
79 let q2_tau_len = results[0].diagnostics.overlap2_tau.len();
80 let n_ckpts = results[0].diagnostics.equil_checkpoints.len();
81
82 let mut agg = SweepResult {
83 mags: vec![0.0; n_temps],
84 mags2: vec![0.0; n_temps],
85 mags4: vec![0.0; n_temps],
86 energies: vec![0.0; n_temps],
87 energies2: vec![0.0; n_temps],
88 overlap: vec![0.0; n_overlap],
89 overlap2: vec![0.0; n_overlap],
90 overlap4: vec![0.0; n_overlap],
91 overlap_histogram: (0..n_overlap_hist)
92 .map(|_| vec![0u64; OVERLAP_HIST_BINS])
93 .collect(),
94 cluster_stats: ClusterStats {
95 fk_csd: (0..n_fk_csd).map(|_| vec![0u64; fk_len]).collect(),
96 overlap_csd: (0..n_ov_csd).map(|_| vec![0u64; ov_len]).collect(),
97 top_cluster_sizes: vec![[0.0; 4]; n_top],
98 },
99 diagnostics: Diagnostics {
100 mags2_tau: vec![0.0; m2_tau_len],
101 overlap2_tau: vec![0.0; q2_tau_len],
102 equil_checkpoints: (0..n_ckpts)
103 .map(|i| EquilCheckpoint {
104 sweep: results[0].diagnostics.equil_checkpoints[i].sweep,
105 energy_avg: vec![0.0; n_temps],
106 link_overlap_avg: vec![0.0; n_temps],
107 })
108 .collect(),
109 },
110 };
111
112 for r in results {
113 for (a, &v) in agg.mags.iter_mut().zip(r.mags.iter()) {
114 *a += v;
115 }
116 for (a, &v) in agg.mags2.iter_mut().zip(r.mags2.iter()) {
117 *a += v;
118 }
119 for (a, &v) in agg.mags4.iter_mut().zip(r.mags4.iter()) {
120 *a += v;
121 }
122 for (a, &v) in agg.energies.iter_mut().zip(r.energies.iter()) {
123 *a += v;
124 }
125 for (a, &v) in agg.energies2.iter_mut().zip(r.energies2.iter()) {
126 *a += v;
127 }
128 for (a, &v) in agg.overlap.iter_mut().zip(r.overlap.iter()) {
129 *a += v;
130 }
131 for (a, &v) in agg.overlap2.iter_mut().zip(r.overlap2.iter()) {
132 *a += v;
133 }
134 for (a, &v) in agg.overlap4.iter_mut().zip(r.overlap4.iter()) {
135 *a += v;
136 }
137 for (a, s) in agg
138 .overlap_histogram
139 .iter_mut()
140 .zip(r.overlap_histogram.iter())
141 {
142 for (ah, &sh) in a.iter_mut().zip(s.iter()) {
143 *ah += sh;
144 }
145 }
146 for (a, s) in agg
147 .cluster_stats
148 .fk_csd
149 .iter_mut()
150 .zip(r.cluster_stats.fk_csd.iter())
151 {
152 for (ah, &sh) in a.iter_mut().zip(s.iter()) {
153 *ah += sh;
154 }
155 }
156 for (a, s) in agg
157 .cluster_stats
158 .overlap_csd
159 .iter_mut()
160 .zip(r.cluster_stats.overlap_csd.iter())
161 {
162 for (ah, &sh) in a.iter_mut().zip(s.iter()) {
163 *ah += sh;
164 }
165 }
166 for (a, &s) in agg
167 .cluster_stats
168 .top_cluster_sizes
169 .iter_mut()
170 .zip(r.cluster_stats.top_cluster_sizes.iter())
171 {
172 for k in 0..4 {
173 a[k] += s[k];
174 }
175 }
176 for (a, &v) in agg
177 .diagnostics
178 .mags2_tau
179 .iter_mut()
180 .zip(r.diagnostics.mags2_tau.iter())
181 {
182 *a += v;
183 }
184 for (a, &v) in agg
185 .diagnostics
186 .overlap2_tau
187 .iter_mut()
188 .zip(r.diagnostics.overlap2_tau.iter())
189 {
190 *a += v;
191 }
192 for (ac, rc) in agg
193 .diagnostics
194 .equil_checkpoints
195 .iter_mut()
196 .zip(r.diagnostics.equil_checkpoints.iter())
197 {
198 for (a, &v) in ac.energy_avg.iter_mut().zip(rc.energy_avg.iter()) {
199 *a += v;
200 }
201 for (a, &v) in ac
202 .link_overlap_avg
203 .iter_mut()
204 .zip(rc.link_overlap_avg.iter())
205 {
206 *a += v;
207 }
208 }
209 }
210
211 for v in agg
212 .mags
213 .iter_mut()
214 .chain(agg.mags2.iter_mut())
215 .chain(agg.mags4.iter_mut())
216 .chain(agg.energies.iter_mut())
217 .chain(agg.energies2.iter_mut())
218 .chain(agg.overlap.iter_mut())
219 .chain(agg.overlap2.iter_mut())
220 .chain(agg.overlap4.iter_mut())
221 {
222 *v /= n;
223 }
224
225 for arr in agg.cluster_stats.top_cluster_sizes.iter_mut() {
226 for v in arr.iter_mut() {
227 *v /= n;
228 }
229 }
230
231 for v in agg.diagnostics.mags2_tau.iter_mut() {
232 *v /= n;
233 }
234 for v in agg.diagnostics.overlap2_tau.iter_mut() {
235 *v /= n;
236 }
237 for ckpt in agg.diagnostics.equil_checkpoints.iter_mut() {
238 for v in ckpt.energy_avg.iter_mut() {
239 *v /= n;
240 }
241 for v in ckpt.link_overlap_avg.iter_mut() {
242 *v /= n;
243 }
244 }
245
246 agg
247 }
248}