max@0
|
1 // Copyright (C) 2009-2011 NICTA (www.nicta.com.au)
|
max@0
|
2 // Copyright (C) 2009-2011 Conrad Sanderson
|
max@0
|
3 //
|
max@0
|
4 // This file is part of the Armadillo C++ library.
|
max@0
|
5 // It is provided without any warranty of fitness
|
max@0
|
6 // for any purpose. You can redistribute this file
|
max@0
|
7 // and/or modify it under the terms of the GNU
|
max@0
|
8 // Lesser General Public License (LGPL) as published
|
max@0
|
9 // by the Free Software Foundation, either version 3
|
max@0
|
10 // of the License or (at your option) any later version.
|
max@0
|
11 // (see http://www.opensource.org/licenses for more info)
|
max@0
|
12
|
max@0
|
13
|
max@0
|
14 //! \addtogroup running_stat
|
max@0
|
15 //! @{
|
max@0
|
16
|
max@0
|
17
|
max@0
|
18
|
max@0
|
19 template<typename eT>
|
max@0
|
20 inline
|
max@0
|
21 arma_counter<eT>::~arma_counter()
|
max@0
|
22 {
|
max@0
|
23 arma_extra_debug_sigprint_this(this);
|
max@0
|
24 }
|
max@0
|
25
|
max@0
|
26
|
max@0
|
27
|
max@0
|
28 template<typename eT>
|
max@0
|
29 inline
|
max@0
|
30 arma_counter<eT>::arma_counter()
|
max@0
|
31 : d_count( eT(0))
|
max@0
|
32 , i_count(uword(0))
|
max@0
|
33 {
|
max@0
|
34 arma_extra_debug_sigprint_this(this);
|
max@0
|
35 }
|
max@0
|
36
|
max@0
|
37
|
max@0
|
38
|
max@0
|
39 template<typename eT>
|
max@0
|
40 inline
|
max@0
|
41 const arma_counter<eT>&
|
max@0
|
42 arma_counter<eT>::operator++()
|
max@0
|
43 {
|
max@0
|
44 if(i_count < ARMA_MAX_UWORD)
|
max@0
|
45 {
|
max@0
|
46 i_count++;
|
max@0
|
47 }
|
max@0
|
48 else
|
max@0
|
49 {
|
max@0
|
50 d_count += eT(ARMA_MAX_UWORD);
|
max@0
|
51 i_count = 0;
|
max@0
|
52 }
|
max@0
|
53
|
max@0
|
54 return *this;
|
max@0
|
55 }
|
max@0
|
56
|
max@0
|
57
|
max@0
|
58
|
max@0
|
59 template<typename eT>
|
max@0
|
60 inline
|
max@0
|
61 void
|
max@0
|
62 arma_counter<eT>::operator++(int)
|
max@0
|
63 {
|
max@0
|
64 operator++();
|
max@0
|
65 }
|
max@0
|
66
|
max@0
|
67
|
max@0
|
68
|
max@0
|
69 template<typename eT>
|
max@0
|
70 inline
|
max@0
|
71 void
|
max@0
|
72 arma_counter<eT>::reset()
|
max@0
|
73 {
|
max@0
|
74 d_count = eT(0);
|
max@0
|
75 i_count = uword(0);
|
max@0
|
76 }
|
max@0
|
77
|
max@0
|
78
|
max@0
|
79
|
max@0
|
80 template<typename eT>
|
max@0
|
81 inline
|
max@0
|
82 eT
|
max@0
|
83 arma_counter<eT>::value() const
|
max@0
|
84 {
|
max@0
|
85 return d_count + eT(i_count);
|
max@0
|
86 }
|
max@0
|
87
|
max@0
|
88
|
max@0
|
89
|
max@0
|
90 template<typename eT>
|
max@0
|
91 inline
|
max@0
|
92 eT
|
max@0
|
93 arma_counter<eT>::value_plus_1() const
|
max@0
|
94 {
|
max@0
|
95 if(i_count < ARMA_MAX_UWORD)
|
max@0
|
96 {
|
max@0
|
97 return d_count + eT(i_count + 1);
|
max@0
|
98 }
|
max@0
|
99 else
|
max@0
|
100 {
|
max@0
|
101 return d_count + eT(ARMA_MAX_UWORD) + eT(1);
|
max@0
|
102 }
|
max@0
|
103 }
|
max@0
|
104
|
max@0
|
105
|
max@0
|
106
|
max@0
|
107 template<typename eT>
|
max@0
|
108 inline
|
max@0
|
109 eT
|
max@0
|
110 arma_counter<eT>::value_minus_1() const
|
max@0
|
111 {
|
max@0
|
112 if(i_count > 0)
|
max@0
|
113 {
|
max@0
|
114 return d_count + eT(i_count - 1);
|
max@0
|
115 }
|
max@0
|
116 else
|
max@0
|
117 {
|
max@0
|
118 return d_count - eT(1);
|
max@0
|
119 }
|
max@0
|
120 }
|
max@0
|
121
|
max@0
|
122
|
max@0
|
123
|
max@0
|
124 //
|
max@0
|
125
|
max@0
|
126
|
max@0
|
127
|
max@0
|
128 template<typename eT>
|
max@0
|
129 running_stat<eT>::~running_stat()
|
max@0
|
130 {
|
max@0
|
131 arma_extra_debug_sigprint_this(this);
|
max@0
|
132 }
|
max@0
|
133
|
max@0
|
134
|
max@0
|
135
|
max@0
|
136 template<typename eT>
|
max@0
|
137 running_stat<eT>::running_stat()
|
max@0
|
138 : r_mean ( eT(0))
|
max@0
|
139 , r_var (typename running_stat<eT>::T(0))
|
max@0
|
140 , min_val ( eT(0))
|
max@0
|
141 , max_val ( eT(0))
|
max@0
|
142 , min_val_norm(typename running_stat<eT>::T(0))
|
max@0
|
143 , max_val_norm(typename running_stat<eT>::T(0))
|
max@0
|
144 {
|
max@0
|
145 arma_extra_debug_sigprint_this(this);
|
max@0
|
146 }
|
max@0
|
147
|
max@0
|
148
|
max@0
|
149
|
max@0
|
150 //! update statistics to reflect new sample
|
max@0
|
151 template<typename eT>
|
max@0
|
152 inline
|
max@0
|
153 void
|
max@0
|
154 running_stat<eT>::operator() (const typename running_stat<eT>::T sample)
|
max@0
|
155 {
|
max@0
|
156 arma_extra_debug_sigprint();
|
max@0
|
157
|
max@0
|
158 if( arma_isfinite(sample) == false )
|
max@0
|
159 {
|
max@0
|
160 arma_warn(true, "running_stat: sample ignored as it is non-finite" );
|
max@0
|
161 return;
|
max@0
|
162 }
|
max@0
|
163
|
max@0
|
164 running_stat_aux::update_stats(*this, sample);
|
max@0
|
165 }
|
max@0
|
166
|
max@0
|
167
|
max@0
|
168
|
max@0
|
169 //! update statistics to reflect new sample (version for complex numbers)
|
max@0
|
170 template<typename eT>
|
max@0
|
171 inline
|
max@0
|
172 void
|
max@0
|
173 running_stat<eT>::operator() (const std::complex< typename running_stat<eT>::T >& sample)
|
max@0
|
174 {
|
max@0
|
175 arma_extra_debug_sigprint();
|
max@0
|
176
|
max@0
|
177 arma_type_check(( is_same_type<eT, std::complex< typename running_stat<eT>::T > >::value == false ));
|
max@0
|
178
|
max@0
|
179 if( arma_isfinite(sample) == false )
|
max@0
|
180 {
|
max@0
|
181 arma_warn(true, "running_stat: sample ignored as it is non-finite" );
|
max@0
|
182 return;
|
max@0
|
183 }
|
max@0
|
184
|
max@0
|
185 running_stat_aux::update_stats(*this, sample);
|
max@0
|
186 }
|
max@0
|
187
|
max@0
|
188
|
max@0
|
189
|
max@0
|
190 //! set all statistics to zero
|
max@0
|
191 template<typename eT>
|
max@0
|
192 inline
|
max@0
|
193 void
|
max@0
|
194 running_stat<eT>::reset()
|
max@0
|
195 {
|
max@0
|
196 arma_extra_debug_sigprint();
|
max@0
|
197
|
max@0
|
198 typedef typename running_stat<eT>::T T;
|
max@0
|
199
|
max@0
|
200 counter.reset();
|
max@0
|
201
|
max@0
|
202 r_mean = eT(0);
|
max@0
|
203 r_var = T(0);
|
max@0
|
204
|
max@0
|
205 min_val = eT(0);
|
max@0
|
206 max_val = eT(0);
|
max@0
|
207
|
max@0
|
208 min_val_norm = T(0);
|
max@0
|
209 max_val_norm = T(0);
|
max@0
|
210 }
|
max@0
|
211
|
max@0
|
212
|
max@0
|
213
|
max@0
|
214 //! mean or average value
|
max@0
|
215 template<typename eT>
|
max@0
|
216 inline
|
max@0
|
217 eT
|
max@0
|
218 running_stat<eT>::mean() const
|
max@0
|
219 {
|
max@0
|
220 arma_extra_debug_sigprint();
|
max@0
|
221
|
max@0
|
222 return r_mean;
|
max@0
|
223 }
|
max@0
|
224
|
max@0
|
225
|
max@0
|
226
|
max@0
|
227 //! variance
|
max@0
|
228 template<typename eT>
|
max@0
|
229 inline
|
max@0
|
230 typename running_stat<eT>::T
|
max@0
|
231 running_stat<eT>::var(const uword norm_type) const
|
max@0
|
232 {
|
max@0
|
233 arma_extra_debug_sigprint();
|
max@0
|
234
|
max@0
|
235 const T N = counter.value();
|
max@0
|
236
|
max@0
|
237 if(N > T(1))
|
max@0
|
238 {
|
max@0
|
239 if(norm_type == 0)
|
max@0
|
240 {
|
max@0
|
241 return r_var;
|
max@0
|
242 }
|
max@0
|
243 else
|
max@0
|
244 {
|
max@0
|
245 const T N_minus_1 = counter.value_minus_1();
|
max@0
|
246 return (N_minus_1/N) * r_var;
|
max@0
|
247 }
|
max@0
|
248 }
|
max@0
|
249 else
|
max@0
|
250 {
|
max@0
|
251 return T(0);
|
max@0
|
252 }
|
max@0
|
253 }
|
max@0
|
254
|
max@0
|
255
|
max@0
|
256
|
max@0
|
257 //! standard deviation
|
max@0
|
258 template<typename eT>
|
max@0
|
259 inline
|
max@0
|
260 typename running_stat<eT>::T
|
max@0
|
261 running_stat<eT>::stddev(const uword norm_type) const
|
max@0
|
262 {
|
max@0
|
263 arma_extra_debug_sigprint();
|
max@0
|
264
|
max@0
|
265 return std::sqrt( (*this).var(norm_type) );
|
max@0
|
266 }
|
max@0
|
267
|
max@0
|
268
|
max@0
|
269
|
max@0
|
270 //! minimum value
|
max@0
|
271 template<typename eT>
|
max@0
|
272 inline
|
max@0
|
273 eT
|
max@0
|
274 running_stat<eT>::min() const
|
max@0
|
275 {
|
max@0
|
276 arma_extra_debug_sigprint();
|
max@0
|
277
|
max@0
|
278 return min_val;
|
max@0
|
279 }
|
max@0
|
280
|
max@0
|
281
|
max@0
|
282
|
max@0
|
283 //! maximum value
|
max@0
|
284 template<typename eT>
|
max@0
|
285 inline
|
max@0
|
286 eT
|
max@0
|
287 running_stat<eT>::max() const
|
max@0
|
288 {
|
max@0
|
289 arma_extra_debug_sigprint();
|
max@0
|
290
|
max@0
|
291 return max_val;
|
max@0
|
292 }
|
max@0
|
293
|
max@0
|
294
|
max@0
|
295
|
max@0
|
296 //! number of samples so far
|
max@0
|
297 template<typename eT>
|
max@0
|
298 inline
|
max@0
|
299 typename get_pod_type<eT>::result
|
max@0
|
300 running_stat<eT>::count() const
|
max@0
|
301 {
|
max@0
|
302 arma_extra_debug_sigprint();
|
max@0
|
303
|
max@0
|
304 return counter.value();
|
max@0
|
305 }
|
max@0
|
306
|
max@0
|
307
|
max@0
|
308
|
max@0
|
309 //! update statistics to reflect new sample
|
max@0
|
310 template<typename eT>
|
max@0
|
311 inline
|
max@0
|
312 void
|
max@0
|
313 running_stat_aux::update_stats(running_stat<eT>& x, const eT sample)
|
max@0
|
314 {
|
max@0
|
315 arma_extra_debug_sigprint();
|
max@0
|
316
|
max@0
|
317 typedef typename running_stat<eT>::T T;
|
max@0
|
318
|
max@0
|
319 const T N = x.counter.value();
|
max@0
|
320
|
max@0
|
321 if(N > T(0))
|
max@0
|
322 {
|
max@0
|
323 if(sample < x.min_val)
|
max@0
|
324 {
|
max@0
|
325 x.min_val = sample;
|
max@0
|
326 }
|
max@0
|
327
|
max@0
|
328 if(sample > x.max_val)
|
max@0
|
329 {
|
max@0
|
330 x.max_val = sample;
|
max@0
|
331 }
|
max@0
|
332
|
max@0
|
333 const T N_plus_1 = x.counter.value_plus_1();
|
max@0
|
334 const T N_minus_1 = x.counter.value_minus_1();
|
max@0
|
335
|
max@0
|
336 // note: variance has to be updated before the mean
|
max@0
|
337
|
max@0
|
338 const eT tmp = sample - x.r_mean;
|
max@0
|
339
|
max@0
|
340 x.r_var = N_minus_1/N * x.r_var + (tmp*tmp)/N_plus_1;
|
max@0
|
341
|
max@0
|
342 x.r_mean = x.r_mean + (sample - x.r_mean)/N_plus_1;
|
max@0
|
343 //x.r_mean = (N/N_plus_1)*x.r_mean + sample/N_plus_1;
|
max@0
|
344 //x.r_mean = (x.r_mean + sample/N) * N/N_plus_1;
|
max@0
|
345 }
|
max@0
|
346 else
|
max@0
|
347 {
|
max@0
|
348 x.r_mean = sample;
|
max@0
|
349 x.min_val = sample;
|
max@0
|
350 x.max_val = sample;
|
max@0
|
351
|
max@0
|
352 // r_var is initialised to zero
|
max@0
|
353 // in the constructor and reset()
|
max@0
|
354 }
|
max@0
|
355
|
max@0
|
356 x.counter++;
|
max@0
|
357 }
|
max@0
|
358
|
max@0
|
359
|
max@0
|
360
|
max@0
|
361 //! update statistics to reflect new sample (version for complex numbers)
|
max@0
|
362 template<typename T>
|
max@0
|
363 inline
|
max@0
|
364 void
|
max@0
|
365 running_stat_aux::update_stats(running_stat< std::complex<T> >& x, const T sample)
|
max@0
|
366 {
|
max@0
|
367 arma_extra_debug_sigprint();
|
max@0
|
368
|
max@0
|
369 running_stat_aux::update_stats(x, std::complex<T>(sample));
|
max@0
|
370 }
|
max@0
|
371
|
max@0
|
372
|
max@0
|
373
|
max@0
|
374 //! alter statistics to reflect new sample (version for complex numbers)
|
max@0
|
375 template<typename T>
|
max@0
|
376 inline
|
max@0
|
377 void
|
max@0
|
378 running_stat_aux::update_stats(running_stat< std::complex<T> >& x, const std::complex<T>& sample)
|
max@0
|
379 {
|
max@0
|
380 arma_extra_debug_sigprint();
|
max@0
|
381
|
max@0
|
382 typedef typename std::complex<T> eT;
|
max@0
|
383
|
max@0
|
384 const T sample_norm = std::norm(sample);
|
max@0
|
385 const T N = x.counter.value();
|
max@0
|
386
|
max@0
|
387 if(N > T(0))
|
max@0
|
388 {
|
max@0
|
389 if(sample_norm < x.min_val_norm)
|
max@0
|
390 {
|
max@0
|
391 x.min_val_norm = sample_norm;
|
max@0
|
392 x.min_val = sample;
|
max@0
|
393 }
|
max@0
|
394
|
max@0
|
395 if(sample_norm > x.max_val_norm)
|
max@0
|
396 {
|
max@0
|
397 x.max_val_norm = sample_norm;
|
max@0
|
398 x.max_val = sample;
|
max@0
|
399 }
|
max@0
|
400
|
max@0
|
401 const T N_plus_1 = x.counter.value_plus_1();
|
max@0
|
402 const T N_minus_1 = x.counter.value_minus_1();
|
max@0
|
403
|
max@0
|
404 x.r_var = N_minus_1/N * x.r_var + std::norm(sample - x.r_mean)/N_plus_1;
|
max@0
|
405
|
max@0
|
406 x.r_mean = x.r_mean + (sample - x.r_mean)/N_plus_1;
|
max@0
|
407 //x.r_mean = (N/N_plus_1)*x.r_mean + sample/N_plus_1;
|
max@0
|
408 //x.r_mean = (x.r_mean + sample/N) * N/N_plus_1;
|
max@0
|
409 }
|
max@0
|
410 else
|
max@0
|
411 {
|
max@0
|
412 x.r_mean = sample;
|
max@0
|
413 x.min_val = sample;
|
max@0
|
414 x.max_val = sample;
|
max@0
|
415 x.min_val_norm = sample_norm;
|
max@0
|
416 x.max_val_norm = sample_norm;
|
max@0
|
417
|
max@0
|
418 // r_var is initialised to zero
|
max@0
|
419 // in the constructor and reset()
|
max@0
|
420 }
|
max@0
|
421
|
max@0
|
422 x.counter++;
|
max@0
|
423 }
|
max@0
|
424
|
max@0
|
425
|
max@0
|
426
|
max@0
|
427 //! @}
|