Browse Source

Statistics: single precision support on Mean/Variance/StandardDeviation #235

netstandard
Christoph Ruegg 11 years ago
parent
commit
c75c9a5e79
  1. 138
      src/Numerics/Statistics/ArrayStatistics.cs
  2. 70
      src/Numerics/Statistics/Statistics.cs
  3. 87
      src/Numerics/Statistics/StreamingStatistics.cs

138
src/Numerics/Statistics/ArrayStatistics.cs

@ -163,6 +163,28 @@ namespace MathNet.Numerics.Statistics
return mean;
}
/// <summary>
/// Estimates the arithmetic sample mean from the unsorted data array.
/// Returns NaN if data is empty or any entry is NaN.
/// </summary>
/// <param name="data">Sample array, no sorting is assumed.</param>
public static double Mean(float[] data)
{
if (data.Length == 0)
{
return float.NaN;
}
double mean = 0;
ulong m = 0;
for (int i = 0; i < data.Length; i++)
{
mean += (data[i] - mean) / ++m;
}
return mean;
}
/// <summary>
/// Evaluates the geometric mean of the unsorted data array.
/// Returns NaN if data is empty or any entry is NaN.
@ -230,6 +252,31 @@ namespace MathNet.Numerics.Statistics
return variance/(samples.Length - 1);
}
/// <summary>
/// Estimates the unbiased population variance from the provided samples as unsorted array.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample array, no sorting is assumed.</param>
public static double Variance(float[] samples)
{
if (samples.Length <= 1)
{
return float.NaN;
}
double variance = 0;
double t = samples[0];
for (int i = 1; i < samples.Length; i++)
{
t += samples[i];
double diff = ((i + 1) * samples[i]) - t;
variance += (diff * diff) / ((i + 1.0) * i);
}
return variance / (samples.Length - 1);
}
/// <summary>
/// Evaluates the population variance from the full population provided as unsorted array.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
@ -255,6 +302,31 @@ namespace MathNet.Numerics.Statistics
return variance/population.Length;
}
/// <summary>
/// Evaluates the population variance from the full population provided as unsorted array.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
/// Returns NaN if data is empty or if any entry is NaN.
/// </summary>
/// <param name="population">Sample array, no sorting is assumed.</param>
public static double PopulationVariance(float[] population)
{
if (population.Length == 0)
{
return float.NaN;
}
double variance = 0;
double t = population[0];
for (int i = 1; i < population.Length; i++)
{
t += population[i];
double diff = ((i + 1) * population[i]) - t;
variance += (diff * diff) / ((i + 1.0) * i);
}
return variance / population.Length;
}
/// <summary>
/// Estimates the unbiased population standard deviation from the provided samples as unsorted array.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -266,6 +338,17 @@ namespace MathNet.Numerics.Statistics
return Math.Sqrt(Variance(samples));
}
/// <summary>
/// Estimates the unbiased population standard deviation from the provided samples as unsorted array.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample array, no sorting is assumed.</param>
public static double StandardDeviation(float[] samples)
{
return Math.Sqrt(Variance(samples));
}
/// <summary>
/// Evaluates the population standard deviation from the full population provided as unsorted array.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
@ -277,6 +360,17 @@ namespace MathNet.Numerics.Statistics
return Math.Sqrt(PopulationVariance(population));
}
/// <summary>
/// Evaluates the population standard deviation from the full population provided as unsorted array.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
/// Returns NaN if data is empty or if any entry is NaN.
/// </summary>
/// <param name="population">Sample array, no sorting is assumed.</param>
public static double PopulationStandardDeviation(float[] population)
{
return Math.Sqrt(PopulationVariance(population));
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population variance from the provided samples as unsorted array.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -288,6 +382,17 @@ namespace MathNet.Numerics.Statistics
return new Tuple<double, double>(Mean(samples), Variance(samples));
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population variance from the provided samples as unsorted array.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN for mean if data is empty or any entry is NaN and NaN for variance if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample array, no sorting is assumed.</param>
public static Tuple<double, double> MeanVariance(float[] samples)
{
return new Tuple<double, double>(Mean(samples), Variance(samples));
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population standard deviation from the provided samples as unsorted array.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -299,6 +404,17 @@ namespace MathNet.Numerics.Statistics
return new Tuple<double, double>(Mean(samples), StandardDeviation(samples));
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population standard deviation from the provided samples as unsorted array.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN for mean if data is empty or any entry is NaN and NaN for standard deviation if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample array, no sorting is assumed.</param>
public static Tuple<double, double> MeanStandardDeviation(float[] samples)
{
return new Tuple<double, double>(Mean(samples), StandardDeviation(samples));
}
/// <summary>
/// Estimates the unbiased population covariance from the provided two sample arrays.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -381,6 +497,28 @@ namespace MathNet.Numerics.Statistics
return Math.Sqrt(mean);
}
/// <summary>
/// Estimates the root mean square (RMS) also known as quadratic mean from the unsorted data array.
/// Returns NaN if data is empty or any entry is NaN.
/// </summary>
/// <param name="data">Sample array, no sorting is assumed.</param>
public static double RootMeanSquare(float[] data)
{
if (data.Length == 0)
{
return double.NaN;
}
double mean = 0;
ulong m = 0;
for (int i = 0; i < data.Length; i++)
{
mean += (data[i] * data[i] - mean) / ++m;
}
return Math.Sqrt(mean);
}
/// <summary>
/// Returns the order statistic (order 1..N) from the unsorted data array.
/// WARNING: Works inplace and can thus causes the data array to be reordered.

70
src/Numerics/Statistics/Statistics.cs

@ -134,6 +134,20 @@ namespace MathNet.Numerics.Statistics
: StreamingStatistics.Mean(data);
}
/// <summary>
/// Evaluates the sample mean, an estimate of the population mean.
/// Returns NaN if data is empty or if any entry is NaN.
/// </summary>
/// <param name="data">The data to calculate the mean of.</param>
/// <returns>The mean of the sample.</returns>
public static double Mean(this IEnumerable<float> data)
{
var array = data as float[];
return array != null
? ArrayStatistics.Mean(array)
: StreamingStatistics.Mean(data);
}
/// <summary>
/// Evaluates the sample mean, an estimate of the population mean.
/// Returns NaN if data is empty or if any entry is NaN.
@ -188,6 +202,20 @@ namespace MathNet.Numerics.Statistics
: StreamingStatistics.Variance(samples);
}
/// <summary>
/// Estimates the unbiased population variance from the provided samples.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">A subset of samples, sampled from the full population.</param>
public static double Variance(this IEnumerable<float> samples)
{
var array = samples as float[];
return array != null
? ArrayStatistics.Variance(array)
: StreamingStatistics.Variance(samples);
}
/// <summary>
/// Estimates the unbiased population variance from the provided samples.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -214,6 +242,20 @@ namespace MathNet.Numerics.Statistics
: StreamingStatistics.PopulationVariance(population);
}
/// <summary>
/// Evaluates the variance from the provided full population.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
/// Returns NaN if data is empty or if any entry is NaN.
/// </summary>
/// <param name="population">The full population data.</param>
public static double PopulationVariance(this IEnumerable<float> population)
{
var array = population as float[];
return array != null
? ArrayStatistics.PopulationVariance(array)
: StreamingStatistics.PopulationVariance(population);
}
/// <summary>
/// Evaluates the variance from the provided full population.
/// On a dataset of size N will use an N normalize and would thus be biased if applied to a subsetr.
@ -240,6 +282,20 @@ namespace MathNet.Numerics.Statistics
: StreamingStatistics.StandardDeviation(samples);
}
/// <summary>
/// Estimates the unbiased population standard deviation from the provided samples.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">A subset of samples, sampled from the full population.</param>
public static double StandardDeviation(this IEnumerable<float> samples)
{
var array = samples as float[];
return array != null
? ArrayStatistics.StandardDeviation(array)
: StreamingStatistics.StandardDeviation(samples);
}
/// <summary>
/// Estimates the unbiased population standard deviation from the provided samples.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -266,6 +322,20 @@ namespace MathNet.Numerics.Statistics
: StreamingStatistics.PopulationStandardDeviation(population);
}
/// <summary>
/// Evaluates the standard deviation from the provided full population.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
/// Returns NaN if data is empty or if any entry is NaN.
/// </summary>
/// <param name="population">The full population data.</param>
public static double PopulationStandardDeviation(this IEnumerable<float> population)
{
var array = population as float[];
return array != null
? ArrayStatistics.PopulationStandardDeviation(array)
: StreamingStatistics.PopulationStandardDeviation(population);
}
/// <summary>
/// Evaluates the standard deviation from the provided full population.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.

87
src/Numerics/Statistics/StreamingStatistics.cs

@ -30,6 +30,7 @@
using System;
using System.Collections.Generic;
using System.Linq;
using MathNet.Numerics.Properties;
namespace MathNet.Numerics.Statistics
@ -155,6 +156,16 @@ namespace MathNet.Numerics.Statistics
return any ? mean : double.NaN;
}
/// <summary>
/// Estimates the arithmetic sample mean from the enumerable, in a single pass without memoization.
/// Returns NaN if data is empty or any entry is NaN.
/// </summary>
/// <param name="stream">Sample stream, no sorting is assumed.</param>
public static double Mean(IEnumerable<float> stream)
{
return Mean(stream.Select(x => (double)x));
}
/// <summary>
/// Evaluates the geometric mean of the enumerable, in a single pass without memoization.
/// Returns NaN if data is empty or any entry is NaN.
@ -226,6 +237,17 @@ namespace MathNet.Numerics.Statistics
return count > 1 ? variance/(count - 1) : double.NaN;
}
/// <summary>
/// Estimates the unbiased population variance from the provided samples as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample stream, no sorting is assumed.</param>
public static double Variance(IEnumerable<float> samples)
{
return Variance(samples.Select(x => (double)x));
}
/// <summary>
/// Evaluates the population variance from the full population provided as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
@ -259,6 +281,17 @@ namespace MathNet.Numerics.Statistics
return variance/count;
}
/// <summary>
/// Evaluates the population variance from the full population provided as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
/// Returns NaN if data is empty or if any entry is NaN.
/// </summary>
/// <param name="population">Sample stream, no sorting is assumed.</param>
public static double PopulationVariance(IEnumerable<float> population)
{
return PopulationVariance(population.Select(x => (double)x));
}
/// <summary>
/// Estimates the unbiased population standard deviation from the provided samples as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -270,6 +303,17 @@ namespace MathNet.Numerics.Statistics
return Math.Sqrt(Variance(samples));
}
/// <summary>
/// Estimates the unbiased population standard deviation from the provided samples as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample stream, no sorting is assumed.</param>
public static double StandardDeviation(IEnumerable<float> samples)
{
return Math.Sqrt(Variance(samples));
}
/// <summary>
/// Evaluates the population standard deviation from the full population provided as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
@ -281,6 +325,17 @@ namespace MathNet.Numerics.Statistics
return Math.Sqrt(PopulationVariance(population));
}
/// <summary>
/// Evaluates the population standard deviation from the full population provided as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N normalizer and would thus be biased if applied to a subset.
/// Returns NaN if data is empty or if any entry is NaN.
/// </summary>
/// <param name="population">Sample stream, no sorting is assumed.</param>
public static double PopulationStandardDeviation(IEnumerable<float> population)
{
return Math.Sqrt(PopulationVariance(population));
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population variance from the provided samples as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -318,6 +373,17 @@ namespace MathNet.Numerics.Statistics
count > 1 ? variance/(count - 1) : double.NaN);
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population variance from the provided samples as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN for mean if data is empty or any entry is NaN, and NaN for variance if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample stream, no sorting is assumed.</param>
public static Tuple<double, double> MeanVariance(IEnumerable<float> samples)
{
return MeanVariance(samples.Select(x => (double)x));
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population standard deviation from the provided samples as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -330,6 +396,17 @@ namespace MathNet.Numerics.Statistics
return new Tuple<double, double>(meanVariance.Item1, Math.Sqrt(meanVariance.Item2));
}
/// <summary>
/// Estimates the arithmetic sample mean and the unbiased population standard deviation from the provided samples as enumerable sequence, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
/// Returns NaN for mean if data is empty or any entry is NaN, and NaN for standard deviation if data has less than two entries or if any entry is NaN.
/// </summary>
/// <param name="samples">Sample stream, no sorting is assumed.</param>
public static Tuple<double, double> MeanStandardDeviation(IEnumerable<float> samples)
{
return MeanStandardDeviation(samples.Select(x => (double)x));
}
/// <summary>
/// Estimates the unbiased population covariance from the provided two sample enumerable sequences, in a single pass without memoization.
/// On a dataset of size N will use an N-1 normalizer (Bessel's correction).
@ -432,6 +509,16 @@ namespace MathNet.Numerics.Statistics
return any ? Math.Sqrt(mean) : double.NaN;
}
/// <summary>
/// Estimates the root mean square (RMS) also known as quadratic mean from the enumerable, in a single pass without memoization.
/// Returns NaN if data is empty or any entry is NaN.
/// </summary>
/// <param name="stream">Sample stream, no sorting is assumed.</param>
public static double RootMeanSquare(IEnumerable<float> stream)
{
return RootMeanSquare(stream.Select(x => (double)x));
}
/// <summary>
/// Calculates the entropy of a stream of double values.
/// Returns NaN if any of the values in the stream are NaN.

Loading…
Cancel
Save