1 #ifndef _theplu_yat_statistics_average_base
2 #define _theplu_yat_statistics_average_base
25 #include <boost/concept_check.hpp>
32 namespace statistics {
68 template<
class Derived>
77 BOOST_CONCEPT_ASSERT((boost::DefaultConstructible<Derived>));
90 void add(
double x,
long n=1) {
static_cast<Derived*
>(
this)->add_impl(x,
n);}
98 {
return n_ ?
mean_ : std::numeric_limits<double>::quiet_NaN(); }
105 long n(
void)
const {
return n_; }
112 void rescale(
double a) {
static_cast<Derived*
>(
this)->rescale_impl(a); }
122 *
static_cast<Derived*
>(
this) = tmp;
144 void add1(
double x,
long int n);
148 void add1(
double delta);
169 template<
class Derived>
198 {
return std::sqrt(
variance()/this->
n()); }
236 {
return sum_xx()/this->
n() + m*m - 2*m*this->
mean();}
259 std::numeric_limits<double>::quiet_NaN();
272 void add2(
double mean,
double cm2,
long int n);
277 void add2(
double delta);
295 template<
class Derived>
348 void add3(
double mean,
double cm2,
double cm3,
long int n);
353 void add3(
double delta);
369 template<
class Derived>
423 void add4(
double mean,
double cm2,
double cm3,
double cm4,
long int n);
428 void add4(
double delta);
439 template<
class Derived>
441 template<
class Derived>
443 template<
class Derived>
445 template<
class Derived>
448 template<
class Derived>
451 if (n == -this->n_) {
455 this->mean_ = (this->n_*this->mean_ + n*x) / (this->n_ + n);
460 template<
class Derived>
464 this->mean_ += delta * 1/(this->n_);
468 template<
class Derived>
471 if (n == -this->n_) {
475 const double delta = this->mean_ - m;
476 this->cm2_ += cm2 + this->n_*n*delta*delta/(this->n_+n);
481 template<
class Derived>
484 this->cm2_ += this->n_*delta*delta/(this->n_+1);
489 template<
class Derived>
493 if (n == -this->n_) {
497 const double n_inverse = 1.0/(this->n_+n);
498 const double delta = mean - this->mean_;
499 const double r = n_inverse*delta;
501 this->cm3_ += cm3 + r*r*delta*this->n_*n*(this->n_-n) +
502 3*r*(this->n_*cm2 - n*this->cm2_);
503 this->add2(mean, cm2, n);
507 template<
class Derived>
510 const double r = delta/(this->n_+1);
512 this->cm3_ += r*r*delta*this->n_*(this->n_-1) - 3*r*this->cm2_;
517 template<
class Derived>
519 double cm4,
long int n)
521 if (n == -this->n_) {
525 const double n_inverse = 1.0/(this->n_+n);
526 const double delta = mean - this->mean_;
527 const double r = n_inverse*delta;
530 std::pow(r,3)*delta*this->n_*n*(this->n_*this->n_-this->n_*n+n*n) +
531 6*r*r*(this->n_*this->n_*cm2+n*n*this->cm2_) +
532 4*r*(this->n_*cm3-n*this->cm3_);
533 this->add3(mean, cm2, cm3, n);
537 template<
class Derived>
540 const double r = delta/(this->n_+1);
543 std::pow(r,3)*delta*this->n_*(this->n_*this->n_-this->n_+1) +
551 template<
class Derived>
559 template<
class Derived>
564 this->cm2_ *= factor;
569 template<
class Derived>
572 double factor = x*this->rescale2(x);
573 this->cm3_ *= factor;
578 template<
class Derived>
581 double factor = x*this->rescale3(x);
582 this->cm3_ *= factor;