criterion/stats/univariate/
mixed.rs
1use rayon::prelude::*;
4use stats::float::Float;
5
6use stats::tuple::{Tuple, TupledDistributionsBuilder};
7use stats::univariate::Resamples;
8use stats::univariate::Sample;
9
10pub fn bootstrap<A, T, S>(
12 a: &Sample<A>,
13 b: &Sample<A>,
14 nresamples: usize,
15 statistic: S,
16) -> T::Distributions
17where
18 A: Float,
19 S: Fn(&Sample<A>, &Sample<A>) -> T + Sync,
20 T: Tuple + Send,
21 T::Distributions: Send,
22 T::Builder: Send,
23{
24 let n_a = a.len();
25 let n_b = b.len();
26 let mut c = Vec::with_capacity(n_a + n_b);
27 c.extend_from_slice(a);
28 c.extend_from_slice(b);
29 let c = Sample::new(&c);
30
31 (0..nresamples)
32 .into_par_iter()
33 .map_init(
34 || Resamples::new(c),
35 |resamples, _| {
36 let resample = resamples.next();
37 let a: &Sample<A> = Sample::new(&resample[..n_a]);
38 let b: &Sample<A> = Sample::new(&resample[n_a..]);
39
40 statistic(a, b)
41 },
42 )
43 .fold(
44 || T::Builder::new(0),
45 |mut sub_distributions, sample| {
46 sub_distributions.push(sample);
47 sub_distributions
48 },
49 )
50 .reduce(
51 || T::Builder::new(0),
52 |mut a, mut b| {
53 a.extend(&mut b);
54 a
55 },
56 )
57 .complete()
58}