New to Rust here, apologies for my naiveté.
I want to define some probability distributions, which obviously have differing parameters. But the "interface" (as I know it in Java) should be the same. At the most basic level each distribution should have a sample
and a sample_many
method. So I implement a trait:
pub trait ERP<T> {
fn sample(&self) -> T;
fn sample_many(&self, i: isize) -> Vec<T>;
}
Then a specific distribution can be created:
pub struct Bernoulli {
pub p: f64
}
impl ERP<bool> for Bernoulli {
fn sample(&self) -> bool {
rand::random::<f64>() < self.p
}
fn sample_many(&self, i: isize) -> Vec<bool> {
(0..i).map(|_| self.sample()).collect()
}
}
My issue is with the sample_many
method, specifically. This method will be the same code regardless of the kind of distribution, e.g.
pub struct Gaussian {
pub mu: f64,
pub sigma: f64
}
impl ERP<f64> for Gaussian {
fn sample(&self) -> f64 {
// Code unique to each distribution
}
fn sample_many(&self, i: isize) -> Vec<f64> {
(0..i).map(|_| self.sample()).collect() // Code reuse??
}
}
So copying the method here is pretty redundant. Is there a way around this?
You can create a default implementation for any function in the trait definition. It can still be overwritten by an implementor
pub trait ERP<T> {
fn sample(&self) -> T;
fn sample_many(&self, i: isize) -> Vec<T> {
(0..i).map(|_| self.sample()).collect()
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With