View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  
18  package org.apache.commons.math.distribution;
19  
20  import java.io.Serializable;
21  
22  import org.apache.commons.math.MathRuntimeException;
23  
24  /**
25   * Default implementation of
26   * {@link org.apache.commons.math.distribution.WeibullDistribution}.
27   *
28   * @since 1.1
29   * @version $Revision: 772119 $ $Date: 2009-05-06 05:43:28 -0400 (Wed, 06 May 2009) $
30   */
31  public class WeibullDistributionImpl extends AbstractContinuousDistribution
32          implements WeibullDistribution, Serializable {
33      
34      /** Serializable version identifier */
35      private static final long serialVersionUID = 8589540077390120676L;
36      
37      /** The shape parameter. */
38      private double alpha;
39      
40      /** The scale parameter. */
41      private double beta;
42      
43      /**
44       * Creates weibull distribution with the given shape and scale and a
45       * location equal to zero.
46       * @param alpha the shape parameter.
47       * @param beta the scale parameter.
48       */
49      public WeibullDistributionImpl(double alpha, double beta){
50          super();
51          setShape(alpha);
52          setScale(beta);
53      }
54  
55      /**
56       * For this distribution, X, this method returns P(X &lt; <code>x</code>).
57       * @param x the value at which the CDF is evaluated.
58       * @return CDF evaluted at <code>x</code>. 
59       */
60      public double cumulativeProbability(double x) {
61          double ret;
62          if (x <= 0.0) {
63              ret = 0.0;
64          } else {
65              ret = 1.0 - Math.exp(-Math.pow(x / getScale(), getShape()));
66          }
67          return ret;
68      }
69  
70      /**
71       * Access the shape parameter.
72       * @return the shape parameter.
73       */
74      public double getShape() {
75          return alpha;
76      }
77      
78      /**
79       * Access the scale parameter.
80       * @return the scale parameter.
81       */
82      public double getScale() {
83          return beta;
84      }
85      
86      /**
87       * For this distribution, X, this method returns the critical point x, such
88       * that P(X &lt; x) = <code>p</code>.
89       * <p>
90       * Returns <code>Double.NEGATIVE_INFINITY</code> for p=0 and 
91       * <code>Double.POSITIVE_INFINITY</code> for p=1.</p>
92       *
93       * @param p the desired probability
94       * @return x, such that P(X &lt; x) = <code>p</code>
95       * @throws IllegalArgumentException if <code>p</code> is not a valid
96       *         probability.
97       */
98      @Override
99      public double inverseCumulativeProbability(double p) {
100         double ret;
101         if (p < 0.0 || p > 1.0) {
102             throw MathRuntimeException.createIllegalArgumentException(
103                   "{0} out of [{1}, {2}] range", p, 0.0, 1.0);
104         } else if (p == 0) {
105             ret = 0.0;
106         } else  if (p == 1) {
107             ret = Double.POSITIVE_INFINITY;
108         } else {
109             ret = getScale() * Math.pow(-Math.log(1.0 - p), 1.0 / getShape());
110         }
111         return ret;
112     }
113     
114     /**
115      * Modify the shape parameter.
116      * @param alpha the new shape parameter value.
117      */
118     public void setShape(double alpha) {
119         if (alpha <= 0.0) {
120             throw MathRuntimeException.createIllegalArgumentException(
121                   "shape must be positive ({0})",
122                   alpha);
123         }       
124         this.alpha = alpha;
125     }
126     
127     /**
128      * Modify the scale parameter.
129      * @param beta the new scale parameter value.
130      */
131     public void setScale(double beta) {
132         if (beta <= 0.0) {
133             throw MathRuntimeException.createIllegalArgumentException(
134                   "scale must be positive ({0})",
135                   beta);
136         }       
137         this.beta = beta;
138     }
139 
140     /**
141      * Access the domain value lower bound, based on <code>p</code>, used to
142      * bracket a CDF root.  This method is used by
143      * {@link #inverseCumulativeProbability(double)} to find critical values.
144      * 
145      * @param p the desired probability for the critical value
146      * @return domain value lower bound, i.e.
147      *         P(X &lt; <i>lower bound</i>) &lt; <code>p</code> 
148      */
149     @Override
150     protected double getDomainLowerBound(double p) {
151         return 0.0;
152     }
153 
154     /**
155      * Access the domain value upper bound, based on <code>p</code>, used to
156      * bracket a CDF root.  This method is used by
157      * {@link #inverseCumulativeProbability(double)} to find critical values.
158      * 
159      * @param p the desired probability for the critical value
160      * @return domain value upper bound, i.e.
161      *         P(X &lt; <i>upper bound</i>) &gt; <code>p</code> 
162      */
163     @Override
164     protected double getDomainUpperBound(double p) {
165         return Double.MAX_VALUE;
166     }
167 
168     /**
169      * Access the initial domain value, based on <code>p</code>, used to
170      * bracket a CDF root.  This method is used by
171      * {@link #inverseCumulativeProbability(double)} to find critical values.
172      * 
173      * @param p the desired probability for the critical value
174      * @return initial domain value
175      */
176     @Override
177     protected double getInitialDomain(double p) {
178         // use median
179         return Math.pow(getScale() * Math.log(2.0), 1.0 / getShape());
180     }
181 }