Beispiel #1
0
 /// <inheritdoc/>
 public override double RawMoment(int r)
 {
     if (r < 0)
     {
         throw new ArgumentOutOfRangeException(nameof(r));
     }
     else
     {
         double[] central = CentralMoments(r);
         return(MomentMath.CentralToRaw(a, central, r));
     }
 }
Beispiel #2
0
 /// <inheritdoc/>
 public override double CentralMoment(int r)
 {
     if (r < 0)
     {
         throw new ArgumentOutOfRangeException(nameof(r));
     }
     else if (r == 0)
     {
         return(1.0);
     }
     else
     {
         double[] K = Cumulants(r);
         return(MomentMath.CumulantToCentral(K, r));
     }
 }
Beispiel #3
0
 /// <inheritdoc />
 public override double RawMoment(int r)
 {
     if (r < 0)
     {
         throw new ArgumentOutOfRangeException(nameof(r));
     }
     else if (r == 0)
     {
         return(1.0);
     }
     else if (r == 1)
     {
         return(Mean);
     }
     else
     {
         double[] C = CentralMoments(r);
         return(MomentMath.CentralToRaw(Mean, C, r));
     }
 }
        /// <inheritdoc />
        public override double CentralMoment(int r)
        {
            if (r < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(r));
            }
            else if (r == 0)
            {
                return(1.0);
            }
            else if (r == 1)
            {
                return(0.0);
            }
            else if (r == 2)
            {
                return(Variance);
            }
            else
            {
                double[] K = Cumulants(r);
                return(MomentMath.CumulantToCentral(K, r));

                // Begin with M_r = e^{r \mu + \frac{1}{2} r^2 \sigma^2} and use
                //     C_r = <(x-M_1)^r> = \sum_{k=0}^{r} {r \choose k} M_k (-M_1)^{r-k}
                //         = \sum_{k=0}^{r} (-1)^{r-k} {r \choose k} e^{k \mu + \frac{1}{2} k^2 \sigma^2} e^{(r-k)(\mu + \frac{1}{2} \sigma^2)}
                //         = e^{r (\mu + \frac{1}{2} \sigma^2)} \sum_{k=0}^{r} (-1)^{r-k} {r \choose k} e^{\frac{1}{2} k (k - 1) \sigma^2}
                // So far, this is just the usual raw to central moment conversion, subject to the usual significant cancellation errors,
                // particularly for small \sigma, in which case all exponentials will be nearly equal. Write
                //     e^{\frac{1}{2} k (k - 1) \sigma^2} = (e^{\frac{1}{2} k (k - 1) \sigma^2} - 1) + 1.
                // When summed over all k, the contribution of the final +1 vanishes, so
                //     C_r = e^{r (\mu + \frac{1}{2} \sigma^2)} \sum_{k=0}^{r} (-1)^{r-k} {r \choose k} (e^{\frac{1}{2} k (k - 1) \sigma^2} - 1)
                // and since ( ) is zero for k = 0 and k = 2, we need not start the sum until k = 2.

                /*
                 * double s = 0.0;
                 * double x = sigma * sigma / 2.0;
                 * for (int k = 2; k <= r; k++) {
                 *  double ds = AdvancedIntegerMath.BinomialCoefficient(r, k) * MoreMath.ExpMinusOne(k * (k - 1) * x);
                 *  if ((r - k) % 2 != 0) ds = -ds;
                 *  s += ds;
                 * }
                 * return (Math.Exp(r * (mu + x)) * s);
                 */
                /*
                 * // This follows from a straightforward expansion of (x-m)^n and substitution of expressions for M_k.
                 * // It eliminates some arithmetic but is still subject to loss of significance due to cancelation.
                 * double s2 = sigma * sigma / 2.0;
                 *
                 * double C = 0.0;
                 * for (int i = 0; i <= r; i++) {
                 *  double dC = AdvancedIntegerMath.BinomialCoefficient(r, i) * Math.Exp((MoreMath.Sqr(r - i) + i) * s2);
                 *  if (i % 2 != 0) dC = -dC;
                 *  C += dC;
                 * }
                 * return (Math.Exp(r * mu) * C);
                 */
                // this isn't great, but it does the job
                // expand in terms of moments about the origin
                // there is likely to be some cancelation, but the distribution is wide enough that it may not matter

                /*
                 * double m = -Mean;
                 * double C = 0.0;
                 * for (int k = 0; k <= n; k++) {
                 *  C += AdvancedIntegerMath.BinomialCoefficient(n, k) * Moment(k) * Math.Pow(m, n - k);
                 * }
                 * return (C);
                 */
            }
        }
 /// <summary>
 /// Computes a central moment of the distribution.
 /// </summary>
 /// <param name="r">The order of the moment to compute.</param>
 /// <returns>The rth central moment of the distribution.</returns>
 /// <seealso cref="RawMoment" />
 public virtual double CentralMoment(int r)
 {
     // This is a terrible way to compute central moments, subject to significant cancelations, so replace it if at all possible.
     double[] M = RawMoments(r);
     return(MomentMath.RawToCentral(M, r));
 }
 /// <summary>
 /// Computes a cumulant of the distribution.
 /// </summary>
 /// <param name="r">The index of the cumulant to compute.</param>
 /// <returns>The rth cumulant of the distribution.</returns>
 /// <seealso href="http://en.wikipedia.org/wiki/Cumulant"/>
 public virtual double Cumulant(int r)
 {
     double[] C = CentralMoments(r);
     double[] K = MomentMath.CentralToCumulant(Mean, C);
     return(K[r]);
 }