#pragma once #include #include #include #include class Quantity { private: double total; double total2; std::vector C; public: unsigned n; std::list hist; Quantity(unsigned lag) : C(lag) { n = 0; total = 0; total2 = 0; } void add(double x) { hist.push_front(x); if (hist.size() > C.size()) { hist.pop_back(); unsigned t = 0; for (double a : hist) { C[t] += a * x; t++; } total += x; total2 += pow(x, 2); n++; } } double avg() const { return total / n; } double avg2() const { return total2 / n; } std::vector ρ() const { double C0 = C.front() / n; double avg2 = pow(total / n, 2); std::vector ρtmp; for (double Ct : C) { ρtmp.push_back((Ct / n - avg2) / (C0 - avg2)); } return ρtmp; } std::array τ() const { double τtmp = 0.5; unsigned M = 1; double c = 8.0; std::vector ρ_tmp = this->ρ(); while (c * τtmp > M && M < C.size()) { τtmp += ρ_tmp[M]; M++; } return {τtmp, 2.0 * (2.0 * M + 1) * pow(τtmp, 2) / n}; } double σ() const { return 2.0 / n * this->τ()[0] * (C[0] / n - pow(this->avg(), 2)); } double serr() const { return sqrt(this->σ()); } unsigned num_added() const { return n; } };