reference_interval/
reference_interval_with_sample.rs1use num_traits::{Float, NumCast};
2use rand::Rng;
3use rand_distr::{Distribution, Normal, StandardNormal};
4use crate::reference_interval::ReferenceInterval;
5use crate::mean::mean;
6
7
8pub struct ReferenceIntervalWithSample<T, F>
11where
12 T: std::ops::Add<Output = T> + std::ops::Sub<Output = T> + Copy,
13 F: Float,
14 StandardNormal: Distribution<F>
15{
16 #[allow(dead_code)]
18 pub reference_interval: ReferenceInterval<T>,
19
20 #[allow(dead_code)]
22 pub mean: F,
23
24 #[allow(dead_code)]
26 pub standard_deviation: F,
27
28 #[allow(dead_code)]
30 pub normal: Normal<F>,
31}
32
33impl<T, F> ReferenceIntervalWithSample<T, F>
34where
35 T: std::ops::Add<Output = T> + std::ops::Sub<Output = T> + Copy + Into<F>,
36 F: Float + NumCast,
37 StandardNormal: Distribution<F>
38{
39 #[allow(dead_code)]
43 pub fn new(reference_interval: ReferenceInterval<T>) -> Self {
44 let lower: F = reference_interval.lower.into();
45 let upper: F = reference_interval.upper.into();
46 let mean: F = mean(lower, upper);
47 let standard_deviation = (mean - lower) / F::from(2.0).unwrap();
48 let normal = Normal::new(mean, standard_deviation).expect("Normal::new");
49 Self {
50 reference_interval: reference_interval,
51 mean: mean,
52 standard_deviation: standard_deviation,
53 normal: normal,
54 }
55 }
56}
57
58impl<T, F> Distribution<F> for ReferenceIntervalWithSample<T, F>
60where
61 T: std::ops::Add<Output = T> + std::ops::Sub<Output = T> + Copy + Into<F>,
62 F: Float + NumCast,
63 StandardNormal: Distribution<F>
64{
65 fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> F {
66 self.normal.sample(rng)
67 }
68}
69
70#[cfg(test)]
71mod tests {
72 use super::*;
73
74 fn subject() -> ReferenceIntervalWithSample<i32, f64> {
75 let reference_interval = ReferenceInterval{
76 units: "units".to_string(),
77 lower: 11,
78 upper: 97,
79 };
80 ReferenceIntervalWithSample::new(reference_interval)
81 }
82
83 #[test]
84 fn test_new() {
85 let x = subject();
86 assert_eq!(x.mean as i32, 54);
87 assert_eq!(x.standard_deviation as i32, 21);
88 }
89
90 #[test]
91 fn test_sample() {
92 let subject = subject();
93 let mut rng = rand::rng();
94 let x: f64 = subject.normal.sample(&mut rng);
95 assert!(x >= 0.0);
96 }
97
98}