public Stats(StatsOptions options)
 {
     m_options      = options;
     m_count        = 0;
     m_min          = Extremum <T> .EmptyMin;
     m_max          = Extremum <T> .EmptyMax;
     m_sum          = KahanSum.Zero;
     m_sumOfSquares = KahanSum.Zero;
 }
        public void Add(Stats <T> s)
        {
            if (s.m_options != m_options)
            {
                throw new ArgumentException("need matching options for adding");
            }

            m_count += s.m_count;
            m_sum.Add(s.m_sum);
            m_min = Extremum <T> .Min(m_min, s.m_min);

            m_max = Extremum <T> .Min(m_max, s.m_max);

            m_sumOfSquares.Add(s.m_sumOfSquares);
        }
        public static Stats <T> operator+(Stats <T> s0, Stats <T> s1)
        {
            if (s0.m_options != s1.m_options)
            {
                throw new ArgumentException("need matching options for adding");
            }

            return(new Stats <T>(s0.m_options)
            {
                m_count = s0.m_count + s1.m_count,
                m_sum = s0.m_sum + s1.m_sum,
                m_min = Extremum <T> .Min(s0.m_min, s1.m_min),
                m_max = Extremum <T> .Min(s0.m_max, s1.m_max),
                m_sumOfSquares = s0.m_sumOfSquares + s1.m_sumOfSquares,
            });
        }
 public static Extremum <T> Min(Extremum <T> e0, Extremum <T> e1)
 {
     return(e0.m_value < e1.m_value ? e0 : e1);
 }
 public static Extremum <T> Max(Extremum <T> e0, Extremum <T> e1)
 {
     return(e0.m_value >= e1.m_value ? e0 : e1);
 }