Skip to content

Commit 319a384

Browse files
authored
Merge pull request #495 from vks/pareto
Implement Pareto distribution
2 parents f8b8ffc + bd7d579 commit 319a384

File tree

2 files changed

+81
-0
lines changed

2 files changed

+81
-0
lines changed

src/distributions/mod.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -158,6 +158,7 @@
158158
//! [`Normal`]: struct.Normal.html
159159
//! [`Open01`]: struct.Open01.html
160160
//! [`OpenClosed01`]: struct.OpenClosed01.html
161+
//! [`Pareto`]: struct.Pareto.html
161162
//! [`Poisson`]: struct.Poisson.html
162163
//! [`Standard`]: struct.Standard.html
163164
//! [`StandardNormal`]: struct.StandardNormal.html
@@ -177,6 +178,8 @@ pub use self::uniform::Uniform as Range;
177178
#[doc(inline)] pub use self::normal::{Normal, LogNormal, StandardNormal};
178179
#[cfg(feature="std")]
179180
#[doc(inline)] pub use self::exponential::{Exp, Exp1};
181+
#[cfg(feature="std")]
182+
#[doc(inline)] pub use self::pareto::Pareto;
180183
#[cfg(feature = "std")]
181184
#[doc(inline)] pub use self::poisson::Poisson;
182185
#[cfg(feature = "std")]
@@ -192,6 +195,8 @@ pub mod uniform;
192195
#[doc(hidden)] pub mod normal;
193196
#[cfg(feature="std")]
194197
#[doc(hidden)] pub mod exponential;
198+
#[cfg(feature="std")]
199+
#[doc(hidden)] pub mod pareto;
195200
#[cfg(feature = "std")]
196201
#[doc(hidden)] pub mod poisson;
197202
#[cfg(feature = "std")]

src/distributions/pareto.rs

Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,76 @@
1+
// Copyright 2018 The Rust Project Developers. See the COPYRIGHT
2+
// file at the top-level directory of this distribution and at
3+
// https://rust-lang.org/COPYRIGHT.
4+
//
5+
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6+
// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7+
// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
8+
// option. This file may not be copied, modified, or distributed
9+
// except according to those terms.
10+
11+
//! The Pareto distribution.
12+
13+
use Rng;
14+
use distributions::{Distribution, OpenClosed01};
15+
16+
/// Samples floating-point numbers according to the Pareto distribution
17+
///
18+
/// # Example
19+
/// ```
20+
/// use rand::prelude::*;
21+
/// use rand::distributions::Pareto;
22+
///
23+
/// let val: f64 = SmallRng::from_entropy().sample(Pareto::new(1., 2.));
24+
/// println!("{}", val);
25+
/// ```
26+
#[derive(Clone, Copy, Debug)]
27+
pub struct Pareto {
28+
scale: f64,
29+
inv_neg_shape: f64,
30+
}
31+
32+
impl Pareto {
33+
/// Construct a new Pareto distribution with given `scale` and `shape`.
34+
///
35+
/// In the literature, `scale` is commonly written as x<sub>m</sub> or k and
36+
/// `shape` is often written as α.
37+
///
38+
/// # Panics
39+
///
40+
/// `scale` and `shape` have to be non-zero and positive.
41+
pub fn new(scale: f64, shape: f64) -> Pareto {
42+
assert!((scale > 0.) & (shape > 0.));
43+
Pareto { scale, inv_neg_shape: -1.0 / shape }
44+
}
45+
}
46+
47+
impl Distribution<f64> for Pareto {
48+
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
49+
let u: f64 = rng.sample(OpenClosed01);
50+
self.scale * u.powf(self.inv_neg_shape)
51+
}
52+
}
53+
54+
#[cfg(test)]
55+
mod tests {
56+
use distributions::Distribution;
57+
use super::Pareto;
58+
59+
#[test]
60+
#[should_panic]
61+
fn invalid() {
62+
Pareto::new(0., 0.);
63+
}
64+
65+
#[test]
66+
fn sample() {
67+
let scale = 1.0;
68+
let shape = 2.0;
69+
let d = Pareto::new(scale, shape);
70+
let mut rng = ::test::rng(1);
71+
for _ in 0..1000 {
72+
let r = d.sample(&mut rng);
73+
assert!(r >= scale);
74+
}
75+
}
76+
}

0 commit comments

Comments
 (0)