Skip to content

Commit

Permalink
build: make rand an optional dependency
Browse files Browse the repository at this point in the history
  • Loading branch information
FreezyLemon committed Sep 9, 2024
1 parent 30aaa45 commit da19f85
Show file tree
Hide file tree
Showing 35 changed files with 117 additions and 89 deletions.
11 changes: 8 additions & 3 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -22,21 +22,26 @@ path = "src/lib.rs"
[[bench]]
name = "order_statistics"
harness = false
required-features = ["rand"]

[features]
default = ["nalgebra"]
default = ["nalgebra", "rand"]
nalgebra = ["dep:nalgebra"]
rand = ["dep:rand", "nalgebra?/rand"]

[dependencies]
rand = "0.8"
approx = "0.5.0"
num-traits = "0.2.14"

[dependencies.rand]
version = "0.8"
optional = true

[dependencies.nalgebra]
version = "0.32"
optional = true
default-features = false
features = ["rand", "std"]
features = ["std"]

[dev-dependencies]
criterion = "0.5"
Expand Down
1 change: 0 additions & 1 deletion benches/order_statistics.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
extern crate rand;
extern crate statrs;
use criterion::{black_box, criterion_group, criterion_main, BatchSize, Criterion};
use rand::prelude::*;
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/bernoulli.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::{Binomial, BinomialError, Discrete, DiscreteCDF};
use crate::statistics::*;
use rand::Rng;

/// Implements the
/// [Bernoulli](https://en.wikipedia.org/wiki/Bernoulli_distribution)
Expand Down Expand Up @@ -85,8 +84,9 @@ impl std::fmt::Display for Bernoulli {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Bernoulli {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
rng.gen_bool(self.p()) as u8 as f64
}
}
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/beta.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
use crate::distribution::{Continuous, ContinuousCDF};
use crate::function::{beta, gamma};
use crate::statistics::*;
use rand::Rng;

/// Implements the [Beta](https://en.wikipedia.org/wiki/Beta_distribution)
/// distribution
Expand Down Expand Up @@ -121,8 +120,9 @@ impl std::fmt::Display for Beta {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Beta {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
// Generated by sampling two gamma distributions and normalizing.
let x = super::gamma::sample_unchecked(rng, self.shape_a, 1.0);
let y = super::gamma::sample_unchecked(rng, self.shape_b, 1.0);
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/binomial.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
use crate::distribution::{Discrete, DiscreteCDF};
use crate::function::{beta, factorial};
use crate::statistics::*;
use rand::Rng;
use std::f64;

/// Implements the
Expand Down Expand Up @@ -110,8 +109,9 @@ impl std::fmt::Display for Binomial {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Binomial {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
(0..self.n).fold(0.0, |acc, _| {
let n: f64 = rng.gen();
if n < self.p {
Expand Down
7 changes: 4 additions & 3 deletions src/distribution/categorical.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::{Discrete, DiscreteCDF};
use crate::statistics::*;
use rand::Rng;
use std::f64;

/// Implements the
Expand Down Expand Up @@ -124,8 +123,9 @@ impl std::fmt::Display for Categorical {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Categorical {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
sample_unchecked(rng, &self.cdf)
}
}
Expand Down Expand Up @@ -322,7 +322,8 @@ impl Discrete<u64, f64> for Categorical {

/// Draws a sample from the categorical distribution described by `cdf`
/// without doing any bounds checking
pub fn sample_unchecked<R: Rng + ?Sized>(rng: &mut R, cdf: &[f64]) -> f64 {
#[cfg(feature = "rand")]
pub fn sample_unchecked<R: ::rand::Rng + ?Sized>(rng: &mut R, cdf: &[f64]) -> f64 {
let draw = rng.gen::<f64>() * cdf.last().unwrap();
cdf.iter()
.enumerate()
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/cauchy.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::{Continuous, ContinuousCDF};
use crate::statistics::*;
use rand::Rng;
use std::f64;

/// Implements the [Cauchy](https://en.wikipedia.org/wiki/Cauchy_distribution)
Expand Down Expand Up @@ -111,8 +110,9 @@ impl std::fmt::Display for Cauchy {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Cauchy {
fn sample<R: Rng + ?Sized>(&self, r: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, r: &mut R) -> f64 {
self.location + self.scale * (f64::consts::PI * (r.gen::<f64>() - 0.5)).tan()
}
}
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/chi.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
use crate::distribution::{Continuous, ContinuousCDF};
use crate::function::gamma;
use crate::statistics::*;
use rand::Rng;
use std::f64;

/// Implements the [Chi](https://en.wikipedia.org/wiki/Chi_distribution)
Expand Down Expand Up @@ -94,8 +93,9 @@ impl std::fmt::Display for Chi {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Chi {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
(0..self.freedom as i64)
.fold(0.0, |acc, _| {
acc + super::normal::sample_unchecked(rng, 0.0, 1.0).powf(2.0)
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/chi_squared.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::{Continuous, ContinuousCDF, Gamma, GammaError};
use crate::statistics::*;
use rand::Rng;
use std::f64;

/// Implements the
Expand Down Expand Up @@ -101,8 +100,9 @@ impl std::fmt::Display for ChiSquared {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for ChiSquared {
fn sample<R: Rng + ?Sized>(&self, r: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, r: &mut R) -> f64 {
::rand::distributions::Distribution::sample(&self.g, r)
}
}
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/dirac.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::ContinuousCDF;
use crate::statistics::*;
use rand::Rng;

/// Implements the [Dirac Delta](https://en.wikipedia.org/wiki/Dirac_delta_function#As_a_distribution)
/// distribution
Expand Down Expand Up @@ -69,8 +68,9 @@ impl std::fmt::Display for Dirac {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Dirac {
fn sample<R: Rng + ?Sized>(&self, _: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, _: &mut R) -> f64 {
self.0
}
}
Expand Down
8 changes: 4 additions & 4 deletions src/distribution/dirichlet.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,7 @@ use crate::distribution::Continuous;
use crate::function::gamma;
use crate::prec;
use crate::statistics::*;
use nalgebra::{Const, Dim, Dyn, OMatrix, OVector};
use rand::Rng;
use nalgebra::{Dim, Dyn, OMatrix, OVector};
use std::f64;

/// Implements the
Expand Down Expand Up @@ -192,16 +191,17 @@ where
}
}

#[cfg(feature = "rand")]
impl<D> ::rand::distributions::Distribution<OVector<f64, D>> for Dirichlet<D>
where
D: Dim,
nalgebra::DefaultAllocator: nalgebra::allocator::Allocator<f64, D>,
{
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> OVector<f64, D> {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> OVector<f64, D> {
let mut sum = 0.0;
OVector::from_iterator_generic(
self.alpha.shape_generic().0,
Const::<1>,
nalgebra::Const::<1>,
self.alpha.iter().map(|&a| {
let sample = super::gamma::sample_unchecked(rng, a, 1.0);
sum += sample;
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/discrete_uniform.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::{Discrete, DiscreteCDF};
use crate::statistics::*;
use rand::Rng;

/// Implements the [Discrete
/// Uniform](https://en.wikipedia.org/wiki/Discrete_uniform_distribution)
Expand Down Expand Up @@ -75,8 +74,9 @@ impl std::fmt::Display for DiscreteUniform {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for DiscreteUniform {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
rng.gen_range(self.min..=self.max) as f64
}
}
Expand Down
8 changes: 5 additions & 3 deletions src/distribution/empirical.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
use crate::distribution::{ContinuousCDF, Uniform};
use crate::distribution::ContinuousCDF;
use crate::statistics::*;
use core::cmp::Ordering;
use rand::Rng;
use std::collections::BTreeMap;

#[derive(Clone, PartialEq, Debug)]
Expand Down Expand Up @@ -176,8 +175,11 @@ impl std::fmt::Display for Empirical {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Empirical {
fn sample<R: ?Sized + Rng>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
use crate::distribution::Uniform;

let uniform = Uniform::new(0.0, 1.0).unwrap();
self.__inverse_cdf(uniform.sample(rng))
}
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/erlang.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::{Continuous, ContinuousCDF, Gamma, GammaError};
use crate::statistics::*;
use rand::Rng;

/// Implements the [Erlang](https://en.wikipedia.org/wiki/Erlang_distribution)
/// distribution
Expand Down Expand Up @@ -83,8 +82,9 @@ impl std::fmt::Display for Erlang {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Erlang {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
::rand::distributions::Distribution::sample(&self.g, rng)
}
}
Expand Down
8 changes: 5 additions & 3 deletions src/distribution/exponential.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::distribution::{ziggurat, Continuous, ContinuousCDF};
use crate::distribution::{Continuous, ContinuousCDF};
use crate::statistics::*;
use rand::Rng;
use std::f64;

/// Implements the
Expand Down Expand Up @@ -91,8 +90,11 @@ impl std::fmt::Display for Exp {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Exp {
fn sample<R: Rng + ?Sized>(&self, r: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, r: &mut R) -> f64 {
use crate::distribution::ziggurat;

ziggurat::sample_exp_1(r) / self.rate
}
}
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/fisher_snedecor.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
use crate::distribution::{Continuous, ContinuousCDF};
use crate::function::beta;
use crate::statistics::*;
use rand::Rng;
use std::f64;

/// Implements the
Expand Down Expand Up @@ -124,8 +123,9 @@ impl std::fmt::Display for FisherSnedecor {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for FisherSnedecor {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
(super::gamma::sample_unchecked(rng, self.freedom_1 / 2.0, 0.5) * self.freedom_2)
/ (super::gamma::sample_unchecked(rng, self.freedom_2 / 2.0, 0.5) * self.freedom_1)
}
Expand Down
7 changes: 4 additions & 3 deletions src/distribution/gamma.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ use crate::distribution::{Continuous, ContinuousCDF};
use crate::function::gamma;
use crate::prec;
use crate::statistics::*;
use rand::Rng;

/// Implements the [Gamma](https://en.wikipedia.org/wiki/Gamma_distribution)
/// distribution
Expand Down Expand Up @@ -122,8 +121,9 @@ impl std::fmt::Display for Gamma {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Gamma {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
sample_unchecked(rng, self.shape, self.rate)
}
}
Expand Down Expand Up @@ -400,7 +400,8 @@ impl Continuous<f64, f64> for Gamma {
///
/// ACM Transactions on Mathematical Software, Vol. 26, No. 3, September 2000,
/// Pages 363-372
pub fn sample_unchecked<R: Rng + ?Sized>(rng: &mut R, shape: f64, rate: f64) -> f64 {
#[cfg(feature = "rand")]
pub fn sample_unchecked<R: ::rand::Rng + ?Sized>(rng: &mut R, shape: f64, rate: f64) -> f64 {
let mut a = shape;
let mut afix = 1.0;
if shape < 1.0 {
Expand Down
7 changes: 4 additions & 3 deletions src/distribution/geometric.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
use crate::distribution::{Discrete, DiscreteCDF};
use crate::statistics::*;
use rand::distributions::OpenClosed01;
use rand::Rng;
use std::f64;

/// Implements the
Expand Down Expand Up @@ -92,8 +90,11 @@ impl std::fmt::Display for Geometric {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Geometric {
fn sample<R: Rng + ?Sized>(&self, r: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, r: &mut R) -> f64 {
use ::rand::distributions::OpenClosed01;

if ulps_eq!(self.p, 1.0) {
1.0
} else {
Expand Down
4 changes: 2 additions & 2 deletions src/distribution/hypergeometric.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
use crate::distribution::{Discrete, DiscreteCDF};
use crate::function::factorial;
use crate::statistics::*;
use rand::Rng;
use std::cmp;
use std::f64;

Expand Down Expand Up @@ -146,8 +145,9 @@ impl std::fmt::Display for Hypergeometric {
}
}

#[cfg(feature = "rand")]
impl ::rand::distributions::Distribution<f64> for Hypergeometric {
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> f64 {
fn sample<R: ::rand::Rng + ?Sized>(&self, rng: &mut R) -> f64 {
let mut population = self.population as f64;
let mut successes = self.successes as f64;
let mut draws = self.draws;
Expand Down
Loading

0 comments on commit da19f85

Please sign in to comment.