| // Copyright ©2016 The gonum Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style |
| // license that can be found in the LICENSE file. |
| |
| package distuv |
| |
| import ( |
| "math" |
| "math/rand" |
| ) |
| |
| // Bernoulli represents a random variable whose value is 1 with probability p and |
| // value of zero with probability 1-P. The value of P must be between 0 and 1. |
| // More information at https://en.wikipedia.org/wiki/Bernoulli_distribution. |
| type Bernoulli struct { |
| P float64 |
| Source *rand.Rand |
| } |
| |
| // CDF computes the value of the cumulative density function at x. |
| func (b Bernoulli) CDF(x float64) float64 { |
| if x < 0 { |
| return 0 |
| } |
| if x < 1 { |
| return 1 - b.P |
| } |
| return 1 |
| } |
| |
| // Entropy returns the entropy of the distribution. |
| func (b Bernoulli) Entropy() float64 { |
| if b.P == 0 { |
| return 0 |
| } |
| if b.P == 1 { |
| return 1 |
| } |
| q := 1 - b.P |
| return -b.P*math.Log(b.P) - q*math.Log(q) |
| } |
| |
| // ExKurtosis returns the excess kurtosis of the distribution. |
| func (b Bernoulli) ExKurtosis() float64 { |
| pq := b.P * (1 - b.P) |
| return (1 - 6*pq) / pq |
| } |
| |
| // LogProb computes the natural logarithm of the value of the probability density function at x. |
| func (b Bernoulli) LogProb(x float64) float64 { |
| if x == 0 { |
| return math.Log(1 - b.P) |
| } |
| if x == 1 { |
| return math.Log(b.P) |
| } |
| return math.Inf(-1) |
| } |
| |
| // Mean returns the mean of the probability distribution. |
| func (b Bernoulli) Mean() float64 { |
| return b.P |
| } |
| |
| // Median returns the median of the probability distribution. |
| func (b Bernoulli) Median() float64 { |
| p := b.P |
| switch { |
| case p < 0.5: |
| return 0 |
| case p > 0.5: |
| return 1 |
| default: |
| return 0.5 |
| } |
| } |
| |
| // NumParameters returns the number of parameters in the distribution. |
| func (Bernoulli) NumParameters() int { |
| return 1 |
| } |
| |
| // Prob computes the value of the probability distribution at x. |
| func (b Bernoulli) Prob(x float64) float64 { |
| return math.Exp(b.LogProb(x)) |
| } |
| |
| // Quantile returns the inverse of the cumulative probability distribution. |
| func (b Bernoulli) Quantile(p float64) float64 { |
| if p < 0 || 1 < p { |
| panic(badPercentile) |
| } |
| if p < 1-b.P { |
| return 0 |
| } |
| return 1 |
| } |
| |
| // Rand returns a random sample drawn from the distribution. |
| func (b Bernoulli) Rand() float64 { |
| var rnd float64 |
| if b.Source == nil { |
| rnd = rand.Float64() |
| } else { |
| rnd = b.Source.Float64() |
| } |
| if rnd < b.P { |
| return 1 |
| } |
| return 0 |
| } |
| |
| // Skewness returns the skewness of the distribution. |
| func (b Bernoulli) Skewness() float64 { |
| return (1 - 2*b.P) / math.Sqrt(b.P*(1-b.P)) |
| } |
| |
| // StdDev returns the standard deviation of the probability distribution. |
| func (b Bernoulli) StdDev() float64 { |
| return math.Sqrt(b.Variance()) |
| } |
| |
| // Survival returns the survival function (complementary CDF) at x. |
| func (b Bernoulli) Survival(x float64) float64 { |
| return 1 - b.CDF(x) |
| } |
| |
| // Variance returns the variance of the probability distribution. |
| func (b Bernoulli) Variance() float64 { |
| return b.P * (1 - b.P) |
| } |