/* *
 * Title:        

* Description:

* Copyright: Copyright (c)

* Company:

* @author * @version 1.0 */ package umontreal.iro.lecuyer.probdist; import umontreal.iro.lecuyer.probdist.NormalDist; import umontreal.iro.lecuyer.util.*; import umontreal.iro.lecuyer.functions.MathFunction; /** * Extends the class {@link ContinuousDistribution} for * the inverse Gaussian distribution with location parameter * μ > 0 and scale parameter * λ > 0. * Its density is *

*

*
* f (x) = (λ/ (2πx^3))1/2e-λ(x-μ)2/(2μ2x),         for x > 0. *

* The distribution function is given by *

*

*
* F(x) = Φ((λ/x)1/2(x/μ -1)) + e2λ/μΦ(- (λ/x)1/2(x/μ + 1)), *

* where Φ is the standard normal distribution function. * *

* The non-static versions of the methods cdf, barF, * and inverseF call the static version of the same name. * */ public class InverseGaussianDist extends ContinuousDistribution { protected double mu; protected double lambda; private static class Function implements MathFunction { protected double mu; protected double lambda; protected double u; public Function (double mu, double lambda, double u) { this.mu = mu; this.lambda = lambda; this.u = u; } public double evaluate (double x) { return u - cdf(mu, lambda, x); } } /** * Constructs the inverse Gaussian distribution with parameters μ and λ. * */ public InverseGaussianDist (double mu, double lambda) { setParams (mu, lambda); } public double density (double x) { return density (mu, lambda, x); } public double cdf (double x) { return cdf (mu, lambda, x); } public double barF (double x) { return barF (mu, lambda, x); } public double inverseF (double u) { return inverseF (mu, lambda, u); } public double getMean() { return getMean (mu, lambda); } public double getVariance() { return getVariance (mu, lambda); } public double getStandardDeviation() { return getStandardDeviation (mu, lambda); } /** * Computes the density function for the * inverse gaussian distribution with parameters μ and λ, * evaluated at x. * */ public static double density (double mu, double lambda, double x) { if (mu <= 0.0) throw new IllegalArgumentException ("mu <= 0"); if (lambda <= 0.0) throw new IllegalArgumentException ("lambda <= 0"); if (x <= 0.0) return 0.0; double sqrtX = Math.sqrt (x); return (Math.sqrt (lambda / (2 * Math.PI)) / (sqrtX * sqrtX * sqrtX) * Math.exp (-lambda * (x - 2 * mu + (mu * mu / x)) / (2 * mu * mu))); } /** * Computes the distribution function * of the inverse gaussian distribution with parameters μ and * λ, evaluated at x. * */ public static double cdf (double mu, double lambda, double x) { if (mu <= 0.0) throw new IllegalArgumentException ("mu <= 0"); if (lambda <= 0.0) throw new IllegalArgumentException ("lambda <= 0"); if (x <= 0.0) return 0.0; double temp = Math.sqrt (lambda / x); double z = temp * (x / mu - 1.0); double w = temp * (x / mu + 1.0); // C'est bien un + dans exp (2 * lambda / mu) return (NormalDist.cdf01 (z) + Math.exp (2 * lambda / mu) * NormalDist.cdf01 (-w)); } /** * Computes the complementary distribution function of the inverse gaussian distribution * with parameters μ and λ, evaluated at x. * */ public static double barF (double mu, double lambda, double x) { return 1.0 - cdf (mu, lambda, x); } /** * Computes the inverse of the inverse gaussian distribution * with parameters μ and λ. * */ public static double inverseF (double mu, double lambda, double u) { if (mu <= 0.0) throw new IllegalArgumentException ("mu <= 0"); if (lambda <= 0.0) throw new IllegalArgumentException ("lambda <= 0"); if (u < 0.0 || u > 1.0) throw new IllegalArgumentException ("u must be in [0,1]"); if (u == 1.0) return Double.POSITIVE_INFINITY; if (u == 0.0) return 0.0; Function f = new Function (mu, lambda, u); // Find interval containing root = x* double sig = getStandardDeviation(mu, lambda); double x0 = 0.0; double x = mu; double v = cdf(mu, lambda, x); while (v < u) { x0 = x; x += 3.0*sig; v = cdf(mu, lambda, x); } return RootFinder.brentDekker (x0, x, f, 1e-12); } /** * Estimates the parameters * (μ, λ) of the inverse gaussian distribution * using the maximum likelihood method, from the n observations * x[i], * i = 0, 1,…, n - 1. The estimates are returned in a two-element * array, in regular order: [μ, λ]. * * @param x the list of observations used to evaluate parameters * * @param n the number of observations used to evaluate parameters * * @return returns the parameters [hat(μ), * hat(λ)] * */ public static double[] getMLE (double[] x, int n) { if (n <= 0) throw new IllegalArgumentException ("n <= 0"); double parameters[]; parameters = new double[2]; double sum = 0; for (int i = 0; i < n; i++) { sum += x[i]; } parameters[0] = sum / (double) n; sum = 0; for (int i = 0; i < n; i++) { sum += ((1.0 / (double) x[i]) - (1.0 / parameters[0])); } parameters[1] = (double) n / (double) sum; return parameters; } /** * Creates a new instance of an inverse gaussian distribution with parameters * μ and λ estimated using the maximum likelihood method based on * the n observations x[i], * i = 0, 1,…, n - 1. * * @param x the list of observations to use to evaluate parameters * * @param n the number of observations to use to evaluate parameters * * */ public static InverseGaussianDist getInstanceFromMLE (double[] x, int n) { double parameters[] = getMLE (x, n); return new InverseGaussianDist (parameters[0], parameters[1]); } /** * Returns the mean * E[X] = μ of the * inverse gaussian distribution with parameters μ and λ. * * @return the mean of the inverse gaussian distribution * E[X] = μ * */ public static double getMean (double mu, double lambda) { if (mu <= 0.0) throw new IllegalArgumentException ("mu <= 0"); if (lambda <= 0.0) throw new IllegalArgumentException ("lambda <= 0"); return mu; } /** * Computes and returns the variance * Var[X] = μ3/λ of * the inverse gaussian distribution with parameters μ and λ. * * @return the variance of the inverse gaussian distribution * * Var[X] = μ3/λ * */ public static double getVariance (double mu, double lambda) { if (mu <= 0.0) throw new IllegalArgumentException ("mu <= 0"); if (lambda <= 0.0) throw new IllegalArgumentException ("lambda <= 0"); return (mu * mu * mu / lambda); } /** * Computes and returns the standard deviation * of the inverse gaussian distribution with parameters μ and λ. * * @return the standard deviation of the inverse gaussian distribution * */ public static double getStandardDeviation (double mu, double lambda) { return Math.sqrt (getVariance (mu, lambda)); } /** * Returns the parameter λ of this object. * */ public double getLambda() { return lambda; } /** * Returns the parameter μ of this object. * */ public double getMu() { return mu; } /** * Sets the parameters μ and λ of this object. * */ public void setParams (double mu, double lambda) { if (mu <= 0.0) throw new IllegalArgumentException ("mu <= 0"); if (lambda <= 0.0) throw new IllegalArgumentException ("lambda <= 0"); this.mu = mu; this.lambda = lambda; supportA = 0.0; } /** * Return a table containing the parameters of the current distribution. * This table is put in regular order: [μ, λ]. * * */ public double[] getParams () { double[] retour = {mu, lambda}; return retour; } public String toString () { return getClass().getSimpleName() + " : mu = " + mu + ", lambda = " + lambda; } }

Ads help maintain this website.